aboutsummaryrefslogtreecommitdiffstats
path: root/drivers/gpu
diff options
context:
space:
mode:
Diffstat (limited to 'drivers/gpu')
-rw-r--r--drivers/gpu/drm/gma500/psb_device.c353
-rw-r--r--drivers/gpu/drm/gma500/psb_gfx.mod.c51
-rw-r--r--drivers/gpu/drm/gma500/psb_intel_display.c1431
-rw-r--r--drivers/gpu/drm/gma500/psb_intel_display.h28
-rw-r--r--drivers/gpu/drm/gma500/psb_intel_drv.h228
-rw-r--r--drivers/gpu/drm/gma500/psb_intel_lvds.c849
-rw-r--r--drivers/gpu/drm/gma500/psb_intel_modes.c77
-rw-r--r--drivers/gpu/drm/gma500/psb_intel_reg.h1235
-rw-r--r--drivers/gpu/drm/gma500/psb_intel_sdvo.c1293
-rw-r--r--drivers/gpu/drm/gma500/psb_intel_sdvo_regs.h338
-rw-r--r--drivers/gpu/drm/gma500/psb_lid.c90
11 files changed, 5973 insertions, 0 deletions
diff --git a/drivers/gpu/drm/gma500/psb_device.c b/drivers/gpu/drm/gma500/psb_device.c
new file mode 100644
index 000000000000..46591323595a
--- /dev/null
+++ b/drivers/gpu/drm/gma500/psb_device.c
@@ -0,0 +1,353 @@
1/**************************************************************************
2 * Copyright (c) 2011, Intel Corporation.
3 * All Rights Reserved.
4 *
5 * This program is free software; you can redistribute it and/or modify it
6 * under the terms and conditions of the GNU General Public License,
7 * version 2, as published by the Free Software Foundation.
8 *
9 * This program is distributed in the hope it will be useful, but WITHOUT
10 * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
11 * FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for
12 * more details.
13 *
14 * You should have received a copy of the GNU General Public License along with
15 * this program; if not, write to the Free Software Foundation, Inc.,
16 * 51 Franklin St - Fifth Floor, Boston, MA 02110-1301 USA.
17 *
18 **************************************************************************/
19
20#include <linux/backlight.h>
21#include <drm/drmP.h>
22#include <drm/drm.h>
23#include "psb_drm.h"
24#include "psb_drv.h"
25#include "psb_reg.h"
26#include "psb_intel_reg.h"
27#include "intel_bios.h"
28
29
30static int psb_output_init(struct drm_device *dev)
31{
32 struct drm_psb_private *dev_priv = dev->dev_private;
33 psb_intel_lvds_init(dev, &dev_priv->mode_dev);
34 psb_intel_sdvo_init(dev, SDVOB);
35 return 0;
36}
37
38#ifdef CONFIG_BACKLIGHT_CLASS_DEVICE
39
40/*
41 * Poulsbo Backlight Interfaces
42 */
43
44#define BLC_PWM_PRECISION_FACTOR 100 /* 10000000 */
45#define BLC_PWM_FREQ_CALC_CONSTANT 32
46#define MHz 1000000
47
48#define PSB_BLC_PWM_PRECISION_FACTOR 10
49#define PSB_BLC_MAX_PWM_REG_FREQ 0xFFFE
50#define PSB_BLC_MIN_PWM_REG_FREQ 0x2
51
52#define PSB_BACKLIGHT_PWM_POLARITY_BIT_CLEAR (0xFFFE)
53#define PSB_BACKLIGHT_PWM_CTL_SHIFT (16)
54
55static int psb_brightness;
56static struct backlight_device *psb_backlight_device;
57
58static int psb_get_brightness(struct backlight_device *bd)
59{
60 /* return locally cached var instead of HW read (due to DPST etc.) */
61 /* FIXME: ideally return actual value in case firmware fiddled with
62 it */
63 return psb_brightness;
64}
65
66
67static int psb_backlight_setup(struct drm_device *dev)
68{
69 struct drm_psb_private *dev_priv = dev->dev_private;
70 unsigned long core_clock;
71 /* u32 bl_max_freq; */
72 /* unsigned long value; */
73 u16 bl_max_freq;
74 uint32_t value;
75 uint32_t blc_pwm_precision_factor;
76
77 /* get bl_max_freq and pol from dev_priv*/
78 if (!dev_priv->lvds_bl) {
79 dev_err(dev->dev, "Has no valid LVDS backlight info\n");
80 return -ENOENT;
81 }
82 bl_max_freq = dev_priv->lvds_bl->freq;
83 blc_pwm_precision_factor = PSB_BLC_PWM_PRECISION_FACTOR;
84
85 core_clock = dev_priv->core_freq;
86
87 value = (core_clock * MHz) / BLC_PWM_FREQ_CALC_CONSTANT;
88 value *= blc_pwm_precision_factor;
89 value /= bl_max_freq;
90 value /= blc_pwm_precision_factor;
91
92 if (value > (unsigned long long)PSB_BLC_MAX_PWM_REG_FREQ ||
93 value < (unsigned long long)PSB_BLC_MIN_PWM_REG_FREQ)
94 return -ERANGE;
95 else {
96 value &= PSB_BACKLIGHT_PWM_POLARITY_BIT_CLEAR;
97 REG_WRITE(BLC_PWM_CTL,
98 (value << PSB_BACKLIGHT_PWM_CTL_SHIFT) | (value));
99 }
100 return 0;
101}
102
103static int psb_set_brightness(struct backlight_device *bd)
104{
105 struct drm_device *dev = bl_get_data(psb_backlight_device);
106 int level = bd->props.brightness;
107
108 /* Percentage 1-100% being valid */
109 if (level < 1)
110 level = 1;
111
112 psb_intel_lvds_set_brightness(dev, level);
113 psb_brightness = level;
114 return 0;
115}
116
117static const struct backlight_ops psb_ops = {
118 .get_brightness = psb_get_brightness,
119 .update_status = psb_set_brightness,
120};
121
122static int psb_backlight_init(struct drm_device *dev)
123{
124 struct drm_psb_private *dev_priv = dev->dev_private;
125 int ret;
126 struct backlight_properties props;
127
128 memset(&props, 0, sizeof(struct backlight_properties));
129 props.max_brightness = 100;
130 props.type = BACKLIGHT_PLATFORM;
131
132 psb_backlight_device = backlight_device_register("psb-bl",
133 NULL, (void *)dev, &psb_ops, &props);
134 if (IS_ERR(psb_backlight_device))
135 return PTR_ERR(psb_backlight_device);
136
137 ret = psb_backlight_setup(dev);
138 if (ret < 0) {
139 backlight_device_unregister(psb_backlight_device);
140 psb_backlight_device = NULL;
141 return ret;
142 }
143 psb_backlight_device->props.brightness = 100;
144 psb_backlight_device->props.max_brightness = 100;
145 backlight_update_status(psb_backlight_device);
146 dev_priv->backlight_device = psb_backlight_device;
147 return 0;
148}
149
150#endif
151
152/*
153 * Provide the Poulsbo specific chip logic and low level methods
154 * for power management
155 */
156
157static void psb_init_pm(struct drm_device *dev)
158{
159 struct drm_psb_private *dev_priv = dev->dev_private;
160
161 u32 gating = PSB_RSGX32(PSB_CR_CLKGATECTL);
162 gating &= ~3; /* Disable 2D clock gating */
163 gating |= 1;
164 PSB_WSGX32(gating, PSB_CR_CLKGATECTL);
165 PSB_RSGX32(PSB_CR_CLKGATECTL);
166}
167
168/**
169 * psb_save_display_registers - save registers lost on suspend
170 * @dev: our DRM device
171 *
172 * Save the state we need in order to be able to restore the interface
173 * upon resume from suspend
174 */
175static int psb_save_display_registers(struct drm_device *dev)
176{
177 struct drm_psb_private *dev_priv = dev->dev_private;
178 struct drm_crtc *crtc;
179 struct drm_connector *connector;
180
181 /* Display arbitration control + watermarks */
182 dev_priv->saveDSPARB = PSB_RVDC32(DSPARB);
183 dev_priv->saveDSPFW1 = PSB_RVDC32(DSPFW1);
184 dev_priv->saveDSPFW2 = PSB_RVDC32(DSPFW2);
185 dev_priv->saveDSPFW3 = PSB_RVDC32(DSPFW3);
186 dev_priv->saveDSPFW4 = PSB_RVDC32(DSPFW4);
187 dev_priv->saveDSPFW5 = PSB_RVDC32(DSPFW5);
188 dev_priv->saveDSPFW6 = PSB_RVDC32(DSPFW6);
189 dev_priv->saveCHICKENBIT = PSB_RVDC32(DSPCHICKENBIT);
190
191 /* Save crtc and output state */
192 mutex_lock(&dev->mode_config.mutex);
193 list_for_each_entry(crtc, &dev->mode_config.crtc_list, head) {
194 if (drm_helper_crtc_in_use(crtc))
195 crtc->funcs->save(crtc);
196 }
197
198 list_for_each_entry(connector, &dev->mode_config.connector_list, head)
199 connector->funcs->save(connector);
200
201 mutex_unlock(&dev->mode_config.mutex);
202 return 0;
203}
204
205/**
206 * psb_restore_display_registers - restore lost register state
207 * @dev: our DRM device
208 *
209 * Restore register state that was lost during suspend and resume.
210 */
211static int psb_restore_display_registers(struct drm_device *dev)
212{
213 struct drm_psb_private *dev_priv = dev->dev_private;
214 struct drm_crtc *crtc;
215 struct drm_connector *connector;
216 int pp_stat;
217
218 /* Display arbitration + watermarks */
219 PSB_WVDC32(dev_priv->saveDSPARB, DSPARB);
220 PSB_WVDC32(dev_priv->saveDSPFW1, DSPFW1);
221 PSB_WVDC32(dev_priv->saveDSPFW2, DSPFW2);
222 PSB_WVDC32(dev_priv->saveDSPFW3, DSPFW3);
223 PSB_WVDC32(dev_priv->saveDSPFW4, DSPFW4);
224 PSB_WVDC32(dev_priv->saveDSPFW5, DSPFW5);
225 PSB_WVDC32(dev_priv->saveDSPFW6, DSPFW6);
226 PSB_WVDC32(dev_priv->saveCHICKENBIT, DSPCHICKENBIT);
227
228 /*make sure VGA plane is off. it initializes to on after reset!*/
229 PSB_WVDC32(0x80000000, VGACNTRL);
230
231 mutex_lock(&dev->mode_config.mutex);
232 list_for_each_entry(crtc, &dev->mode_config.crtc_list, head)
233 if (drm_helper_crtc_in_use(crtc))
234 crtc->funcs->restore(crtc);
235
236 list_for_each_entry(connector, &dev->mode_config.connector_list, head)
237 connector->funcs->restore(connector);
238
239 mutex_unlock(&dev->mode_config.mutex);
240
241 if (dev_priv->iLVDS_enable) {
242 /*shutdown the panel*/
243 PSB_WVDC32(0, PP_CONTROL);
244 do {
245 pp_stat = PSB_RVDC32(PP_STATUS);
246 } while (pp_stat & 0x80000000);
247
248 /* Turn off the plane */
249 PSB_WVDC32(0x58000000, DSPACNTR);
250 PSB_WVDC32(0, DSPASURF);/*trigger the plane disable*/
251 /* Wait ~4 ticks */
252 msleep(4);
253 /* Turn off pipe */
254 PSB_WVDC32(0x0, PIPEACONF);
255 /* Wait ~8 ticks */
256 msleep(8);
257
258 /* Turn off PLLs */
259 PSB_WVDC32(0, MRST_DPLL_A);
260 } else {
261 PSB_WVDC32(DPI_SHUT_DOWN, DPI_CONTROL_REG);
262 PSB_WVDC32(0x0, PIPEACONF);
263 PSB_WVDC32(0x2faf0000, BLC_PWM_CTL);
264 while (REG_READ(0x70008) & 0x40000000)
265 cpu_relax();
266 while ((PSB_RVDC32(GEN_FIFO_STAT_REG) & DPI_FIFO_EMPTY)
267 != DPI_FIFO_EMPTY)
268 cpu_relax();
269 PSB_WVDC32(0, DEVICE_READY_REG);
270 }
271 return 0;
272}
273
274static int psb_power_down(struct drm_device *dev)
275{
276 return 0;
277}
278
279static int psb_power_up(struct drm_device *dev)
280{
281 return 0;
282}
283
284static void psb_get_core_freq(struct drm_device *dev)
285{
286 uint32_t clock;
287 struct pci_dev *pci_root = pci_get_bus_and_slot(0, 0);
288 struct drm_psb_private *dev_priv = dev->dev_private;
289
290 /*pci_write_config_dword(pci_root, 0xD4, 0x00C32004);*/
291 /*pci_write_config_dword(pci_root, 0xD0, 0xE0033000);*/
292
293 pci_write_config_dword(pci_root, 0xD0, 0xD0050300);
294 pci_read_config_dword(pci_root, 0xD4, &clock);
295 pci_dev_put(pci_root);
296
297 switch (clock & 0x07) {
298 case 0:
299 dev_priv->core_freq = 100;
300 break;
301 case 1:
302 dev_priv->core_freq = 133;
303 break;
304 case 2:
305 dev_priv->core_freq = 150;
306 break;
307 case 3:
308 dev_priv->core_freq = 178;
309 break;
310 case 4:
311 dev_priv->core_freq = 200;
312 break;
313 case 5:
314 case 6:
315 case 7:
316 dev_priv->core_freq = 266;
317 default:
318 dev_priv->core_freq = 0;
319 }
320}
321
322static int psb_chip_setup(struct drm_device *dev)
323{
324 psb_get_core_freq(dev);
325 gma_intel_opregion_init(dev);
326 psb_intel_init_bios(dev);
327 return 0;
328}
329
330const struct psb_ops psb_chip_ops = {
331 .name = "Poulsbo",
332 .accel_2d = 1,
333 .pipes = 2,
334 .crtcs = 2,
335 .sgx_offset = PSB_SGX_OFFSET,
336 .chip_setup = psb_chip_setup,
337
338 .crtc_helper = &psb_intel_helper_funcs,
339 .crtc_funcs = &psb_intel_crtc_funcs,
340
341 .output_init = psb_output_init,
342
343#ifdef CONFIG_BACKLIGHT_CLASS_DEVICE
344 .backlight_init = psb_backlight_init,
345#endif
346
347 .init_pm = psb_init_pm,
348 .save_regs = psb_save_display_registers,
349 .restore_regs = psb_restore_display_registers,
350 .power_down = psb_power_down,
351 .power_up = psb_power_up,
352};
353
diff --git a/drivers/gpu/drm/gma500/psb_gfx.mod.c b/drivers/gpu/drm/gma500/psb_gfx.mod.c
new file mode 100644
index 000000000000..3c0bfdfce1e5
--- /dev/null
+++ b/drivers/gpu/drm/gma500/psb_gfx.mod.c
@@ -0,0 +1,51 @@
1#include <linux/module.h>
2#include <linux/vermagic.h>
3#include <linux/compiler.h>
4
5MODULE_INFO(vermagic, VERMAGIC_STRING);
6
7struct module __this_module
8__attribute__((section(".gnu.linkonce.this_module"))) = {
9 .name = KBUILD_MODNAME,
10 .init = init_module,
11#ifdef CONFIG_MODULE_UNLOAD
12 .exit = cleanup_module,
13#endif
14 .arch = MODULE_ARCH_INIT,
15};
16
17MODULE_INFO(staging, "Y");
18
19static const char __module_depends[]
20__used
21__attribute__((section(".modinfo"))) =
22"depends=drm,drm_kms_helper,video,i2c-algo-bit";
23
24MODULE_ALIAS("pci:v00008086d00008108sv*sd*bc*sc*i*");
25MODULE_ALIAS("pci:v00008086d00008109sv*sd*bc*sc*i*");
26MODULE_ALIAS("pci:v00008086d00004100sv*sd*bc*sc*i*");
27MODULE_ALIAS("pci:v00008086d00004101sv*sd*bc*sc*i*");
28MODULE_ALIAS("pci:v00008086d00004102sv*sd*bc*sc*i*");
29MODULE_ALIAS("pci:v00008086d00004103sv*sd*bc*sc*i*");
30MODULE_ALIAS("pci:v00008086d00004104sv*sd*bc*sc*i*");
31MODULE_ALIAS("pci:v00008086d00004105sv*sd*bc*sc*i*");
32MODULE_ALIAS("pci:v00008086d00004106sv*sd*bc*sc*i*");
33MODULE_ALIAS("pci:v00008086d00004107sv*sd*bc*sc*i*");
34MODULE_ALIAS("pci:v00008086d00000130sv*sd*bc*sc*i*");
35MODULE_ALIAS("pci:v00008086d00000131sv*sd*bc*sc*i*");
36MODULE_ALIAS("pci:v00008086d00000132sv*sd*bc*sc*i*");
37MODULE_ALIAS("pci:v00008086d00000133sv*sd*bc*sc*i*");
38MODULE_ALIAS("pci:v00008086d00000134sv*sd*bc*sc*i*");
39MODULE_ALIAS("pci:v00008086d00000135sv*sd*bc*sc*i*");
40MODULE_ALIAS("pci:v00008086d00000136sv*sd*bc*sc*i*");
41MODULE_ALIAS("pci:v00008086d00000137sv*sd*bc*sc*i*");
42MODULE_ALIAS("pci:v00008086d00000BE0sv*sd*bc*sc*i*");
43MODULE_ALIAS("pci:v00008086d00000BE1sv*sd*bc*sc*i*");
44MODULE_ALIAS("pci:v00008086d00000BE2sv*sd*bc*sc*i*");
45MODULE_ALIAS("pci:v00008086d00000BE3sv*sd*bc*sc*i*");
46MODULE_ALIAS("pci:v00008086d00000BE4sv*sd*bc*sc*i*");
47MODULE_ALIAS("pci:v00008086d00000BE5sv*sd*bc*sc*i*");
48MODULE_ALIAS("pci:v00008086d00000BE6sv*sd*bc*sc*i*");
49MODULE_ALIAS("pci:v00008086d00000BE7sv*sd*bc*sc*i*");
50
51MODULE_INFO(srcversion, "51B3334F342F5EEAC93AF22");
diff --git a/drivers/gpu/drm/gma500/psb_intel_display.c b/drivers/gpu/drm/gma500/psb_intel_display.c
new file mode 100644
index 000000000000..ab650765a647
--- /dev/null
+++ b/drivers/gpu/drm/gma500/psb_intel_display.c
@@ -0,0 +1,1431 @@
1/*
2 * Copyright © 2006-2011 Intel Corporation
3 *
4 * This program is free software; you can redistribute it and/or modify it
5 * under the terms and conditions of the GNU General Public License,
6 * version 2, as published by the Free Software Foundation.
7 *
8 * This program is distributed in the hope it will be useful, but WITHOUT
9 * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
10 * FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for
11 * more details.
12 *
13 * You should have received a copy of the GNU General Public License along with
14 * this program; if not, write to the Free Software Foundation, Inc.,
15 * 51 Franklin St - Fifth Floor, Boston, MA 02110-1301 USA.
16 *
17 * Authors:
18 * Eric Anholt <eric@anholt.net>
19 */
20
21#include <linux/i2c.h>
22#include <linux/pm_runtime.h>
23
24#include <drm/drmP.h>
25#include "framebuffer.h"
26#include "psb_drv.h"
27#include "psb_intel_drv.h"
28#include "psb_intel_reg.h"
29#include "psb_intel_display.h"
30#include "power.h"
31
32struct psb_intel_clock_t {
33 /* given values */
34 int n;
35 int m1, m2;
36 int p1, p2;
37 /* derived values */
38 int dot;
39 int vco;
40 int m;
41 int p;
42};
43
44struct psb_intel_range_t {
45 int min, max;
46};
47
48struct psb_intel_p2_t {
49 int dot_limit;
50 int p2_slow, p2_fast;
51};
52
53#define INTEL_P2_NUM 2
54
55struct psb_intel_limit_t {
56 struct psb_intel_range_t dot, vco, n, m, m1, m2, p, p1;
57 struct psb_intel_p2_t p2;
58};
59
60#define I8XX_DOT_MIN 25000
61#define I8XX_DOT_MAX 350000
62#define I8XX_VCO_MIN 930000
63#define I8XX_VCO_MAX 1400000
64#define I8XX_N_MIN 3
65#define I8XX_N_MAX 16
66#define I8XX_M_MIN 96
67#define I8XX_M_MAX 140
68#define I8XX_M1_MIN 18
69#define I8XX_M1_MAX 26
70#define I8XX_M2_MIN 6
71#define I8XX_M2_MAX 16
72#define I8XX_P_MIN 4
73#define I8XX_P_MAX 128
74#define I8XX_P1_MIN 2
75#define I8XX_P1_MAX 33
76#define I8XX_P1_LVDS_MIN 1
77#define I8XX_P1_LVDS_MAX 6
78#define I8XX_P2_SLOW 4
79#define I8XX_P2_FAST 2
80#define I8XX_P2_LVDS_SLOW 14
81#define I8XX_P2_LVDS_FAST 14 /* No fast option */
82#define I8XX_P2_SLOW_LIMIT 165000
83
84#define I9XX_DOT_MIN 20000
85#define I9XX_DOT_MAX 400000
86#define I9XX_VCO_MIN 1400000
87#define I9XX_VCO_MAX 2800000
88#define I9XX_N_MIN 3
89#define I9XX_N_MAX 8
90#define I9XX_M_MIN 70
91#define I9XX_M_MAX 120
92#define I9XX_M1_MIN 10
93#define I9XX_M1_MAX 20
94#define I9XX_M2_MIN 5
95#define I9XX_M2_MAX 9
96#define I9XX_P_SDVO_DAC_MIN 5
97#define I9XX_P_SDVO_DAC_MAX 80
98#define I9XX_P_LVDS_MIN 7
99#define I9XX_P_LVDS_MAX 98
100#define I9XX_P1_MIN 1
101#define I9XX_P1_MAX 8
102#define I9XX_P2_SDVO_DAC_SLOW 10
103#define I9XX_P2_SDVO_DAC_FAST 5
104#define I9XX_P2_SDVO_DAC_SLOW_LIMIT 200000
105#define I9XX_P2_LVDS_SLOW 14
106#define I9XX_P2_LVDS_FAST 7
107#define I9XX_P2_LVDS_SLOW_LIMIT 112000
108
109#define INTEL_LIMIT_I8XX_DVO_DAC 0
110#define INTEL_LIMIT_I8XX_LVDS 1
111#define INTEL_LIMIT_I9XX_SDVO_DAC 2
112#define INTEL_LIMIT_I9XX_LVDS 3
113
114static const struct psb_intel_limit_t psb_intel_limits[] = {
115 { /* INTEL_LIMIT_I8XX_DVO_DAC */
116 .dot = {.min = I8XX_DOT_MIN, .max = I8XX_DOT_MAX},
117 .vco = {.min = I8XX_VCO_MIN, .max = I8XX_VCO_MAX},
118 .n = {.min = I8XX_N_MIN, .max = I8XX_N_MAX},
119 .m = {.min = I8XX_M_MIN, .max = I8XX_M_MAX},
120 .m1 = {.min = I8XX_M1_MIN, .max = I8XX_M1_MAX},
121 .m2 = {.min = I8XX_M2_MIN, .max = I8XX_M2_MAX},
122 .p = {.min = I8XX_P_MIN, .max = I8XX_P_MAX},
123 .p1 = {.min = I8XX_P1_MIN, .max = I8XX_P1_MAX},
124 .p2 = {.dot_limit = I8XX_P2_SLOW_LIMIT,
125 .p2_slow = I8XX_P2_SLOW, .p2_fast = I8XX_P2_FAST},
126 },
127 { /* INTEL_LIMIT_I8XX_LVDS */
128 .dot = {.min = I8XX_DOT_MIN, .max = I8XX_DOT_MAX},
129 .vco = {.min = I8XX_VCO_MIN, .max = I8XX_VCO_MAX},
130 .n = {.min = I8XX_N_MIN, .max = I8XX_N_MAX},
131 .m = {.min = I8XX_M_MIN, .max = I8XX_M_MAX},
132 .m1 = {.min = I8XX_M1_MIN, .max = I8XX_M1_MAX},
133 .m2 = {.min = I8XX_M2_MIN, .max = I8XX_M2_MAX},
134 .p = {.min = I8XX_P_MIN, .max = I8XX_P_MAX},
135 .p1 = {.min = I8XX_P1_LVDS_MIN, .max = I8XX_P1_LVDS_MAX},
136 .p2 = {.dot_limit = I8XX_P2_SLOW_LIMIT,
137 .p2_slow = I8XX_P2_LVDS_SLOW, .p2_fast = I8XX_P2_LVDS_FAST},
138 },
139 { /* INTEL_LIMIT_I9XX_SDVO_DAC */
140 .dot = {.min = I9XX_DOT_MIN, .max = I9XX_DOT_MAX},
141 .vco = {.min = I9XX_VCO_MIN, .max = I9XX_VCO_MAX},
142 .n = {.min = I9XX_N_MIN, .max = I9XX_N_MAX},
143 .m = {.min = I9XX_M_MIN, .max = I9XX_M_MAX},
144 .m1 = {.min = I9XX_M1_MIN, .max = I9XX_M1_MAX},
145 .m2 = {.min = I9XX_M2_MIN, .max = I9XX_M2_MAX},
146 .p = {.min = I9XX_P_SDVO_DAC_MIN, .max = I9XX_P_SDVO_DAC_MAX},
147 .p1 = {.min = I9XX_P1_MIN, .max = I9XX_P1_MAX},
148 .p2 = {.dot_limit = I9XX_P2_SDVO_DAC_SLOW_LIMIT,
149 .p2_slow = I9XX_P2_SDVO_DAC_SLOW, .p2_fast =
150 I9XX_P2_SDVO_DAC_FAST},
151 },
152 { /* INTEL_LIMIT_I9XX_LVDS */
153 .dot = {.min = I9XX_DOT_MIN, .max = I9XX_DOT_MAX},
154 .vco = {.min = I9XX_VCO_MIN, .max = I9XX_VCO_MAX},
155 .n = {.min = I9XX_N_MIN, .max = I9XX_N_MAX},
156 .m = {.min = I9XX_M_MIN, .max = I9XX_M_MAX},
157 .m1 = {.min = I9XX_M1_MIN, .max = I9XX_M1_MAX},
158 .m2 = {.min = I9XX_M2_MIN, .max = I9XX_M2_MAX},
159 .p = {.min = I9XX_P_LVDS_MIN, .max = I9XX_P_LVDS_MAX},
160 .p1 = {.min = I9XX_P1_MIN, .max = I9XX_P1_MAX},
161 /* The single-channel range is 25-112Mhz, and dual-channel
162 * is 80-224Mhz. Prefer single channel as much as possible.
163 */
164 .p2 = {.dot_limit = I9XX_P2_LVDS_SLOW_LIMIT,
165 .p2_slow = I9XX_P2_LVDS_SLOW, .p2_fast = I9XX_P2_LVDS_FAST},
166 },
167};
168
169static const struct psb_intel_limit_t *psb_intel_limit(struct drm_crtc *crtc)
170{
171 const struct psb_intel_limit_t *limit;
172
173 if (psb_intel_pipe_has_type(crtc, INTEL_OUTPUT_LVDS))
174 limit = &psb_intel_limits[INTEL_LIMIT_I9XX_LVDS];
175 else
176 limit = &psb_intel_limits[INTEL_LIMIT_I9XX_SDVO_DAC];
177 return limit;
178}
179
180/** Derive the pixel clock for the given refclk and divisors for 8xx chips. */
181
182static void i8xx_clock(int refclk, struct psb_intel_clock_t *clock)
183{
184 clock->m = 5 * (clock->m1 + 2) + (clock->m2 + 2);
185 clock->p = clock->p1 * clock->p2;
186 clock->vco = refclk * clock->m / (clock->n + 2);
187 clock->dot = clock->vco / clock->p;
188}
189
190/** Derive the pixel clock for the given refclk and divisors for 9xx chips. */
191
192static void i9xx_clock(int refclk, struct psb_intel_clock_t *clock)
193{
194 clock->m = 5 * (clock->m1 + 2) + (clock->m2 + 2);
195 clock->p = clock->p1 * clock->p2;
196 clock->vco = refclk * clock->m / (clock->n + 2);
197 clock->dot = clock->vco / clock->p;
198}
199
200static void psb_intel_clock(struct drm_device *dev, int refclk,
201 struct psb_intel_clock_t *clock)
202{
203 return i9xx_clock(refclk, clock);
204}
205
206/**
207 * Returns whether any output on the specified pipe is of the specified type
208 */
209bool psb_intel_pipe_has_type(struct drm_crtc *crtc, int type)
210{
211 struct drm_device *dev = crtc->dev;
212 struct drm_mode_config *mode_config = &dev->mode_config;
213 struct drm_connector *l_entry;
214
215 list_for_each_entry(l_entry, &mode_config->connector_list, head) {
216 if (l_entry->encoder && l_entry->encoder->crtc == crtc) {
217 struct psb_intel_output *psb_intel_output =
218 to_psb_intel_output(l_entry);
219 if (psb_intel_output->type == type)
220 return true;
221 }
222 }
223 return false;
224}
225
226#define INTELPllInvalid(s) { /* ErrorF (s) */; return false; }
227/**
228 * Returns whether the given set of divisors are valid for a given refclk with
229 * the given connectors.
230 */
231
232static bool psb_intel_PLL_is_valid(struct drm_crtc *crtc,
233 struct psb_intel_clock_t *clock)
234{
235 const struct psb_intel_limit_t *limit = psb_intel_limit(crtc);
236
237 if (clock->p1 < limit->p1.min || limit->p1.max < clock->p1)
238 INTELPllInvalid("p1 out of range\n");
239 if (clock->p < limit->p.min || limit->p.max < clock->p)
240 INTELPllInvalid("p out of range\n");
241 if (clock->m2 < limit->m2.min || limit->m2.max < clock->m2)
242 INTELPllInvalid("m2 out of range\n");
243 if (clock->m1 < limit->m1.min || limit->m1.max < clock->m1)
244 INTELPllInvalid("m1 out of range\n");
245 if (clock->m1 <= clock->m2)
246 INTELPllInvalid("m1 <= m2\n");
247 if (clock->m < limit->m.min || limit->m.max < clock->m)
248 INTELPllInvalid("m out of range\n");
249 if (clock->n < limit->n.min || limit->n.max < clock->n)
250 INTELPllInvalid("n out of range\n");
251 if (clock->vco < limit->vco.min || limit->vco.max < clock->vco)
252 INTELPllInvalid("vco out of range\n");
253 /* XXX: We may need to be checking "Dot clock"
254 * depending on the multiplier, connector, etc.,
255 * rather than just a single range.
256 */
257 if (clock->dot < limit->dot.min || limit->dot.max < clock->dot)
258 INTELPllInvalid("dot out of range\n");
259
260 return true;
261}
262
263/**
264 * Returns a set of divisors for the desired target clock with the given
265 * refclk, or FALSE. The returned values represent the clock equation:
266 * reflck * (5 * (m1 + 2) + (m2 + 2)) / (n + 2) / p1 / p2.
267 */
268static bool psb_intel_find_best_PLL(struct drm_crtc *crtc, int target,
269 int refclk,
270 struct psb_intel_clock_t *best_clock)
271{
272 struct drm_device *dev = crtc->dev;
273 struct psb_intel_clock_t clock;
274 const struct psb_intel_limit_t *limit = psb_intel_limit(crtc);
275 int err = target;
276
277 if (psb_intel_pipe_has_type(crtc, INTEL_OUTPUT_LVDS) &&
278 (REG_READ(LVDS) & LVDS_PORT_EN) != 0) {
279 /*
280 * For LVDS, if the panel is on, just rely on its current
281 * settings for dual-channel. We haven't figured out how to
282 * reliably set up different single/dual channel state, if we
283 * even can.
284 */
285 if ((REG_READ(LVDS) & LVDS_CLKB_POWER_MASK) ==
286 LVDS_CLKB_POWER_UP)
287 clock.p2 = limit->p2.p2_fast;
288 else
289 clock.p2 = limit->p2.p2_slow;
290 } else {
291 if (target < limit->p2.dot_limit)
292 clock.p2 = limit->p2.p2_slow;
293 else
294 clock.p2 = limit->p2.p2_fast;
295 }
296
297 memset(best_clock, 0, sizeof(*best_clock));
298
299 for (clock.m1 = limit->m1.min; clock.m1 <= limit->m1.max;
300 clock.m1++) {
301 for (clock.m2 = limit->m2.min;
302 clock.m2 < clock.m1 && clock.m2 <= limit->m2.max;
303 clock.m2++) {
304 for (clock.n = limit->n.min;
305 clock.n <= limit->n.max; clock.n++) {
306 for (clock.p1 = limit->p1.min;
307 clock.p1 <= limit->p1.max;
308 clock.p1++) {
309 int this_err;
310
311 psb_intel_clock(dev, refclk, &clock);
312
313 if (!psb_intel_PLL_is_valid
314 (crtc, &clock))
315 continue;
316
317 this_err = abs(clock.dot - target);
318 if (this_err < err) {
319 *best_clock = clock;
320 err = this_err;
321 }
322 }
323 }
324 }
325 }
326
327 return err != target;
328}
329
330void psb_intel_wait_for_vblank(struct drm_device *dev)
331{
332 /* Wait for 20ms, i.e. one cycle at 50hz. */
333 mdelay(20);
334}
335
336int psb_intel_pipe_set_base(struct drm_crtc *crtc,
337 int x, int y, struct drm_framebuffer *old_fb)
338{
339 struct drm_device *dev = crtc->dev;
340 /* struct drm_i915_master_private *master_priv; */
341 struct psb_intel_crtc *psb_intel_crtc = to_psb_intel_crtc(crtc);
342 struct psb_framebuffer *psbfb = to_psb_fb(crtc->fb);
343 int pipe = psb_intel_crtc->pipe;
344 unsigned long start, offset;
345 int dspbase = (pipe == 0 ? DSPABASE : DSPBBASE);
346 int dspsurf = (pipe == 0 ? DSPASURF : DSPBSURF);
347 int dspstride = (pipe == 0) ? DSPASTRIDE : DSPBSTRIDE;
348 int dspcntr_reg = (pipe == 0) ? DSPACNTR : DSPBCNTR;
349 u32 dspcntr;
350 int ret = 0;
351
352 if (!gma_power_begin(dev, true))
353 return 0;
354
355 /* no fb bound */
356 if (!crtc->fb) {
357 dev_dbg(dev->dev, "No FB bound\n");
358 goto psb_intel_pipe_cleaner;
359 }
360
361 /* We are displaying this buffer, make sure it is actually loaded
362 into the GTT */
363 ret = psb_gtt_pin(psbfb->gtt);
364 if (ret < 0)
365 goto psb_intel_pipe_set_base_exit;
366 start = psbfb->gtt->offset;
367
368 offset = y * crtc->fb->pitch + x * (crtc->fb->bits_per_pixel / 8);
369
370 REG_WRITE(dspstride, crtc->fb->pitch);
371
372 dspcntr = REG_READ(dspcntr_reg);
373 dspcntr &= ~DISPPLANE_PIXFORMAT_MASK;
374
375 switch (crtc->fb->bits_per_pixel) {
376 case 8:
377 dspcntr |= DISPPLANE_8BPP;
378 break;
379 case 16:
380 if (crtc->fb->depth == 15)
381 dspcntr |= DISPPLANE_15_16BPP;
382 else
383 dspcntr |= DISPPLANE_16BPP;
384 break;
385 case 24:
386 case 32:
387 dspcntr |= DISPPLANE_32BPP_NO_ALPHA;
388 break;
389 default:
390 dev_err(dev->dev, "Unknown color depth\n");
391 ret = -EINVAL;
392 psb_gtt_unpin(psbfb->gtt);
393 goto psb_intel_pipe_set_base_exit;
394 }
395 REG_WRITE(dspcntr_reg, dspcntr);
396
397
398 if (0 /* FIXMEAC - check what PSB needs */) {
399 REG_WRITE(dspbase, offset);
400 REG_READ(dspbase);
401 REG_WRITE(dspsurf, start);
402 REG_READ(dspsurf);
403 } else {
404 REG_WRITE(dspbase, start + offset);
405 REG_READ(dspbase);
406 }
407
408psb_intel_pipe_cleaner:
409 /* If there was a previous display we can now unpin it */
410 if (old_fb)
411 psb_gtt_unpin(to_psb_fb(old_fb)->gtt);
412
413psb_intel_pipe_set_base_exit:
414 gma_power_end(dev);
415 return ret;
416}
417
418/**
419 * Sets the power management mode of the pipe and plane.
420 *
421 * This code should probably grow support for turning the cursor off and back
422 * on appropriately at the same time as we're turning the pipe off/on.
423 */
424static void psb_intel_crtc_dpms(struct drm_crtc *crtc, int mode)
425{
426 struct drm_device *dev = crtc->dev;
427 /* struct drm_i915_master_private *master_priv; */
428 /* struct drm_i915_private *dev_priv = dev->dev_private; */
429 struct psb_intel_crtc *psb_intel_crtc = to_psb_intel_crtc(crtc);
430 int pipe = psb_intel_crtc->pipe;
431 int dpll_reg = (pipe == 0) ? DPLL_A : DPLL_B;
432 int dspcntr_reg = (pipe == 0) ? DSPACNTR : DSPBCNTR;
433 int dspbase_reg = (pipe == 0) ? DSPABASE : DSPBBASE;
434 int pipeconf_reg = (pipe == 0) ? PIPEACONF : PIPEBCONF;
435 u32 temp;
436 bool enabled;
437
438 /* XXX: When our outputs are all unaware of DPMS modes other than off
439 * and on, we should map those modes to DRM_MODE_DPMS_OFF in the CRTC.
440 */
441 switch (mode) {
442 case DRM_MODE_DPMS_ON:
443 case DRM_MODE_DPMS_STANDBY:
444 case DRM_MODE_DPMS_SUSPEND:
445 /* Enable the DPLL */
446 temp = REG_READ(dpll_reg);
447 if ((temp & DPLL_VCO_ENABLE) == 0) {
448 REG_WRITE(dpll_reg, temp);
449 REG_READ(dpll_reg);
450 /* Wait for the clocks to stabilize. */
451 udelay(150);
452 REG_WRITE(dpll_reg, temp | DPLL_VCO_ENABLE);
453 REG_READ(dpll_reg);
454 /* Wait for the clocks to stabilize. */
455 udelay(150);
456 REG_WRITE(dpll_reg, temp | DPLL_VCO_ENABLE);
457 REG_READ(dpll_reg);
458 /* Wait for the clocks to stabilize. */
459 udelay(150);
460 }
461
462 /* Enable the pipe */
463 temp = REG_READ(pipeconf_reg);
464 if ((temp & PIPEACONF_ENABLE) == 0)
465 REG_WRITE(pipeconf_reg, temp | PIPEACONF_ENABLE);
466
467 /* Enable the plane */
468 temp = REG_READ(dspcntr_reg);
469 if ((temp & DISPLAY_PLANE_ENABLE) == 0) {
470 REG_WRITE(dspcntr_reg,
471 temp | DISPLAY_PLANE_ENABLE);
472 /* Flush the plane changes */
473 REG_WRITE(dspbase_reg, REG_READ(dspbase_reg));
474 }
475
476 psb_intel_crtc_load_lut(crtc);
477
478 /* Give the overlay scaler a chance to enable
479 * if it's on this pipe */
480 /* psb_intel_crtc_dpms_video(crtc, true); TODO */
481 break;
482 case DRM_MODE_DPMS_OFF:
483 /* Give the overlay scaler a chance to disable
484 * if it's on this pipe */
485 /* psb_intel_crtc_dpms_video(crtc, FALSE); TODO */
486
487 /* Disable the VGA plane that we never use */
488 REG_WRITE(VGACNTRL, VGA_DISP_DISABLE);
489
490 /* Disable display plane */
491 temp = REG_READ(dspcntr_reg);
492 if ((temp & DISPLAY_PLANE_ENABLE) != 0) {
493 REG_WRITE(dspcntr_reg,
494 temp & ~DISPLAY_PLANE_ENABLE);
495 /* Flush the plane changes */
496 REG_WRITE(dspbase_reg, REG_READ(dspbase_reg));
497 REG_READ(dspbase_reg);
498 }
499
500 /* Next, disable display pipes */
501 temp = REG_READ(pipeconf_reg);
502 if ((temp & PIPEACONF_ENABLE) != 0) {
503 REG_WRITE(pipeconf_reg, temp & ~PIPEACONF_ENABLE);
504 REG_READ(pipeconf_reg);
505 }
506
507 /* Wait for vblank for the disable to take effect. */
508 psb_intel_wait_for_vblank(dev);
509
510 temp = REG_READ(dpll_reg);
511 if ((temp & DPLL_VCO_ENABLE) != 0) {
512 REG_WRITE(dpll_reg, temp & ~DPLL_VCO_ENABLE);
513 REG_READ(dpll_reg);
514 }
515
516 /* Wait for the clocks to turn off. */
517 udelay(150);
518 break;
519 }
520
521 enabled = crtc->enabled && mode != DRM_MODE_DPMS_OFF;
522
523 /*Set FIFO Watermarks*/
524 REG_WRITE(DSPARB, 0x3F3E);
525}
526
527static void psb_intel_crtc_prepare(struct drm_crtc *crtc)
528{
529 struct drm_crtc_helper_funcs *crtc_funcs = crtc->helper_private;
530 crtc_funcs->dpms(crtc, DRM_MODE_DPMS_OFF);
531}
532
533static void psb_intel_crtc_commit(struct drm_crtc *crtc)
534{
535 struct drm_crtc_helper_funcs *crtc_funcs = crtc->helper_private;
536 crtc_funcs->dpms(crtc, DRM_MODE_DPMS_ON);
537}
538
539void psb_intel_encoder_prepare(struct drm_encoder *encoder)
540{
541 struct drm_encoder_helper_funcs *encoder_funcs =
542 encoder->helper_private;
543 /* lvds has its own version of prepare see psb_intel_lvds_prepare */
544 encoder_funcs->dpms(encoder, DRM_MODE_DPMS_OFF);
545}
546
547void psb_intel_encoder_commit(struct drm_encoder *encoder)
548{
549 struct drm_encoder_helper_funcs *encoder_funcs =
550 encoder->helper_private;
551 /* lvds has its own version of commit see psb_intel_lvds_commit */
552 encoder_funcs->dpms(encoder, DRM_MODE_DPMS_ON);
553}
554
555static bool psb_intel_crtc_mode_fixup(struct drm_crtc *crtc,
556 struct drm_display_mode *mode,
557 struct drm_display_mode *adjusted_mode)
558{
559 return true;
560}
561
562
563/**
564 * Return the pipe currently connected to the panel fitter,
565 * or -1 if the panel fitter is not present or not in use
566 */
567static int psb_intel_panel_fitter_pipe(struct drm_device *dev)
568{
569 u32 pfit_control;
570
571 pfit_control = REG_READ(PFIT_CONTROL);
572
573 /* See if the panel fitter is in use */
574 if ((pfit_control & PFIT_ENABLE) == 0)
575 return -1;
576 /* Must be on PIPE 1 for PSB */
577 return 1;
578}
579
580static int psb_intel_crtc_mode_set(struct drm_crtc *crtc,
581 struct drm_display_mode *mode,
582 struct drm_display_mode *adjusted_mode,
583 int x, int y,
584 struct drm_framebuffer *old_fb)
585{
586 struct drm_device *dev = crtc->dev;
587 struct psb_intel_crtc *psb_intel_crtc = to_psb_intel_crtc(crtc);
588 struct drm_crtc_helper_funcs *crtc_funcs = crtc->helper_private;
589 int pipe = psb_intel_crtc->pipe;
590 int fp_reg = (pipe == 0) ? FPA0 : FPB0;
591 int dpll_reg = (pipe == 0) ? DPLL_A : DPLL_B;
592 int dspcntr_reg = (pipe == 0) ? DSPACNTR : DSPBCNTR;
593 int pipeconf_reg = (pipe == 0) ? PIPEACONF : PIPEBCONF;
594 int htot_reg = (pipe == 0) ? HTOTAL_A : HTOTAL_B;
595 int hblank_reg = (pipe == 0) ? HBLANK_A : HBLANK_B;
596 int hsync_reg = (pipe == 0) ? HSYNC_A : HSYNC_B;
597 int vtot_reg = (pipe == 0) ? VTOTAL_A : VTOTAL_B;
598 int vblank_reg = (pipe == 0) ? VBLANK_A : VBLANK_B;
599 int vsync_reg = (pipe == 0) ? VSYNC_A : VSYNC_B;
600 int dspsize_reg = (pipe == 0) ? DSPASIZE : DSPBSIZE;
601 int dsppos_reg = (pipe == 0) ? DSPAPOS : DSPBPOS;
602 int pipesrc_reg = (pipe == 0) ? PIPEASRC : PIPEBSRC;
603 int refclk;
604 struct psb_intel_clock_t clock;
605 u32 dpll = 0, fp = 0, dspcntr, pipeconf;
606 bool ok, is_sdvo = false, is_dvo = false;
607 bool is_crt = false, is_lvds = false, is_tv = false;
608 struct drm_mode_config *mode_config = &dev->mode_config;
609 struct drm_connector *connector;
610
611 /* No scan out no play */
612 if (crtc->fb == NULL) {
613 crtc_funcs->mode_set_base(crtc, x, y, old_fb);
614 return 0;
615 }
616
617 list_for_each_entry(connector, &mode_config->connector_list, head) {
618 struct psb_intel_output *psb_intel_output =
619 to_psb_intel_output(connector);
620
621 if (!connector->encoder
622 || connector->encoder->crtc != crtc)
623 continue;
624
625 switch (psb_intel_output->type) {
626 case INTEL_OUTPUT_LVDS:
627 is_lvds = true;
628 break;
629 case INTEL_OUTPUT_SDVO:
630 is_sdvo = true;
631 break;
632 case INTEL_OUTPUT_DVO:
633 is_dvo = true;
634 break;
635 case INTEL_OUTPUT_TVOUT:
636 is_tv = true;
637 break;
638 case INTEL_OUTPUT_ANALOG:
639 is_crt = true;
640 break;
641 }
642 }
643
644 refclk = 96000;
645
646 ok = psb_intel_find_best_PLL(crtc, adjusted_mode->clock, refclk,
647 &clock);
648 if (!ok) {
649 dev_err(dev->dev, "Couldn't find PLL settings for mode!\n");
650 return 0;
651 }
652
653 fp = clock.n << 16 | clock.m1 << 8 | clock.m2;
654
655 dpll = DPLL_VGA_MODE_DIS;
656 if (is_lvds) {
657 dpll |= DPLLB_MODE_LVDS;
658 dpll |= DPLL_DVO_HIGH_SPEED;
659 } else
660 dpll |= DPLLB_MODE_DAC_SERIAL;
661 if (is_sdvo) {
662 int sdvo_pixel_multiply =
663 adjusted_mode->clock / mode->clock;
664 dpll |= DPLL_DVO_HIGH_SPEED;
665 dpll |=
666 (sdvo_pixel_multiply - 1) << SDVO_MULTIPLIER_SHIFT_HIRES;
667 }
668
669 /* compute bitmask from p1 value */
670 dpll |= (1 << (clock.p1 - 1)) << 16;
671 switch (clock.p2) {
672 case 5:
673 dpll |= DPLL_DAC_SERIAL_P2_CLOCK_DIV_5;
674 break;
675 case 7:
676 dpll |= DPLLB_LVDS_P2_CLOCK_DIV_7;
677 break;
678 case 10:
679 dpll |= DPLL_DAC_SERIAL_P2_CLOCK_DIV_10;
680 break;
681 case 14:
682 dpll |= DPLLB_LVDS_P2_CLOCK_DIV_14;
683 break;
684 }
685
686 if (is_tv) {
687 /* XXX: just matching BIOS for now */
688/* dpll |= PLL_REF_INPUT_TVCLKINBC; */
689 dpll |= 3;
690 }
691 dpll |= PLL_REF_INPUT_DREFCLK;
692
693 /* setup pipeconf */
694 pipeconf = REG_READ(pipeconf_reg);
695
696 /* Set up the display plane register */
697 dspcntr = DISPPLANE_GAMMA_ENABLE;
698
699 if (pipe == 0)
700 dspcntr |= DISPPLANE_SEL_PIPE_A;
701 else
702 dspcntr |= DISPPLANE_SEL_PIPE_B;
703
704 dspcntr |= DISPLAY_PLANE_ENABLE;
705 pipeconf |= PIPEACONF_ENABLE;
706 dpll |= DPLL_VCO_ENABLE;
707
708
709 /* Disable the panel fitter if it was on our pipe */
710 if (psb_intel_panel_fitter_pipe(dev) == pipe)
711 REG_WRITE(PFIT_CONTROL, 0);
712
713 drm_mode_debug_printmodeline(mode);
714
715 if (dpll & DPLL_VCO_ENABLE) {
716 REG_WRITE(fp_reg, fp);
717 REG_WRITE(dpll_reg, dpll & ~DPLL_VCO_ENABLE);
718 REG_READ(dpll_reg);
719 udelay(150);
720 }
721
722 /* The LVDS pin pair needs to be on before the DPLLs are enabled.
723 * This is an exception to the general rule that mode_set doesn't turn
724 * things on.
725 */
726 if (is_lvds) {
727 u32 lvds = REG_READ(LVDS);
728
729 lvds &= ~LVDS_PIPEB_SELECT;
730 if (pipe == 1)
731 lvds |= LVDS_PIPEB_SELECT;
732
733 lvds |= LVDS_PORT_EN | LVDS_A0A2_CLKA_POWER_UP;
734 /* Set the B0-B3 data pairs corresponding to
735 * whether we're going to
736 * set the DPLLs for dual-channel mode or not.
737 */
738 lvds &= ~(LVDS_B0B3_POWER_UP | LVDS_CLKB_POWER_UP);
739 if (clock.p2 == 7)
740 lvds |= LVDS_B0B3_POWER_UP | LVDS_CLKB_POWER_UP;
741
742 /* It would be nice to set 24 vs 18-bit mode (LVDS_A3_POWER_UP)
743 * appropriately here, but we need to look more
744 * thoroughly into how panels behave in the two modes.
745 */
746
747 REG_WRITE(LVDS, lvds);
748 REG_READ(LVDS);
749 }
750
751 REG_WRITE(fp_reg, fp);
752 REG_WRITE(dpll_reg, dpll);
753 REG_READ(dpll_reg);
754 /* Wait for the clocks to stabilize. */
755 udelay(150);
756
757 /* write it again -- the BIOS does, after all */
758 REG_WRITE(dpll_reg, dpll);
759
760 REG_READ(dpll_reg);
761 /* Wait for the clocks to stabilize. */
762 udelay(150);
763
764 REG_WRITE(htot_reg, (adjusted_mode->crtc_hdisplay - 1) |
765 ((adjusted_mode->crtc_htotal - 1) << 16));
766 REG_WRITE(hblank_reg, (adjusted_mode->crtc_hblank_start - 1) |
767 ((adjusted_mode->crtc_hblank_end - 1) << 16));
768 REG_WRITE(hsync_reg, (adjusted_mode->crtc_hsync_start - 1) |
769 ((adjusted_mode->crtc_hsync_end - 1) << 16));
770 REG_WRITE(vtot_reg, (adjusted_mode->crtc_vdisplay - 1) |
771 ((adjusted_mode->crtc_vtotal - 1) << 16));
772 REG_WRITE(vblank_reg, (adjusted_mode->crtc_vblank_start - 1) |
773 ((adjusted_mode->crtc_vblank_end - 1) << 16));
774 REG_WRITE(vsync_reg, (adjusted_mode->crtc_vsync_start - 1) |
775 ((adjusted_mode->crtc_vsync_end - 1) << 16));
776 /* pipesrc and dspsize control the size that is scaled from,
777 * which should always be the user's requested size.
778 */
779 REG_WRITE(dspsize_reg,
780 ((mode->vdisplay - 1) << 16) | (mode->hdisplay - 1));
781 REG_WRITE(dsppos_reg, 0);
782 REG_WRITE(pipesrc_reg,
783 ((mode->hdisplay - 1) << 16) | (mode->vdisplay - 1));
784 REG_WRITE(pipeconf_reg, pipeconf);
785 REG_READ(pipeconf_reg);
786
787 psb_intel_wait_for_vblank(dev);
788
789 REG_WRITE(dspcntr_reg, dspcntr);
790
791 /* Flush the plane changes */
792 crtc_funcs->mode_set_base(crtc, x, y, old_fb);
793
794 psb_intel_wait_for_vblank(dev);
795
796 return 0;
797}
798
799/** Loads the palette/gamma unit for the CRTC with the prepared values */
800void psb_intel_crtc_load_lut(struct drm_crtc *crtc)
801{
802 struct drm_device *dev = crtc->dev;
803 struct drm_psb_private *dev_priv =
804 (struct drm_psb_private *)dev->dev_private;
805 struct psb_intel_crtc *psb_intel_crtc = to_psb_intel_crtc(crtc);
806 int palreg = PALETTE_A;
807 int i;
808
809 /* The clocks have to be on to load the palette. */
810 if (!crtc->enabled)
811 return;
812
813 switch (psb_intel_crtc->pipe) {
814 case 0:
815 break;
816 case 1:
817 palreg = PALETTE_B;
818 break;
819 case 2:
820 palreg = PALETTE_C;
821 break;
822 default:
823 dev_err(dev->dev, "Illegal Pipe Number.\n");
824 return;
825 }
826
827 if (gma_power_begin(dev, false)) {
828 for (i = 0; i < 256; i++) {
829 REG_WRITE(palreg + 4 * i,
830 ((psb_intel_crtc->lut_r[i] +
831 psb_intel_crtc->lut_adj[i]) << 16) |
832 ((psb_intel_crtc->lut_g[i] +
833 psb_intel_crtc->lut_adj[i]) << 8) |
834 (psb_intel_crtc->lut_b[i] +
835 psb_intel_crtc->lut_adj[i]));
836 }
837 gma_power_end(dev);
838 } else {
839 for (i = 0; i < 256; i++) {
840 dev_priv->save_palette_a[i] =
841 ((psb_intel_crtc->lut_r[i] +
842 psb_intel_crtc->lut_adj[i]) << 16) |
843 ((psb_intel_crtc->lut_g[i] +
844 psb_intel_crtc->lut_adj[i]) << 8) |
845 (psb_intel_crtc->lut_b[i] +
846 psb_intel_crtc->lut_adj[i]);
847 }
848
849 }
850}
851
852/**
853 * Save HW states of giving crtc
854 */
855static void psb_intel_crtc_save(struct drm_crtc *crtc)
856{
857 struct drm_device *dev = crtc->dev;
858 /* struct drm_psb_private *dev_priv =
859 (struct drm_psb_private *)dev->dev_private; */
860 struct psb_intel_crtc *psb_intel_crtc = to_psb_intel_crtc(crtc);
861 struct psb_intel_crtc_state *crtc_state = psb_intel_crtc->crtc_state;
862 int pipeA = (psb_intel_crtc->pipe == 0);
863 uint32_t paletteReg;
864 int i;
865
866 if (!crtc_state) {
867 dev_err(dev->dev, "No CRTC state found\n");
868 return;
869 }
870
871 crtc_state->saveDSPCNTR = REG_READ(pipeA ? DSPACNTR : DSPBCNTR);
872 crtc_state->savePIPECONF = REG_READ(pipeA ? PIPEACONF : PIPEBCONF);
873 crtc_state->savePIPESRC = REG_READ(pipeA ? PIPEASRC : PIPEBSRC);
874 crtc_state->saveFP0 = REG_READ(pipeA ? FPA0 : FPB0);
875 crtc_state->saveFP1 = REG_READ(pipeA ? FPA1 : FPB1);
876 crtc_state->saveDPLL = REG_READ(pipeA ? DPLL_A : DPLL_B);
877 crtc_state->saveHTOTAL = REG_READ(pipeA ? HTOTAL_A : HTOTAL_B);
878 crtc_state->saveHBLANK = REG_READ(pipeA ? HBLANK_A : HBLANK_B);
879 crtc_state->saveHSYNC = REG_READ(pipeA ? HSYNC_A : HSYNC_B);
880 crtc_state->saveVTOTAL = REG_READ(pipeA ? VTOTAL_A : VTOTAL_B);
881 crtc_state->saveVBLANK = REG_READ(pipeA ? VBLANK_A : VBLANK_B);
882 crtc_state->saveVSYNC = REG_READ(pipeA ? VSYNC_A : VSYNC_B);
883 crtc_state->saveDSPSTRIDE = REG_READ(pipeA ? DSPASTRIDE : DSPBSTRIDE);
884
885 /*NOTE: DSPSIZE DSPPOS only for psb*/
886 crtc_state->saveDSPSIZE = REG_READ(pipeA ? DSPASIZE : DSPBSIZE);
887 crtc_state->saveDSPPOS = REG_READ(pipeA ? DSPAPOS : DSPBPOS);
888
889 crtc_state->saveDSPBASE = REG_READ(pipeA ? DSPABASE : DSPBBASE);
890
891 paletteReg = pipeA ? PALETTE_A : PALETTE_B;
892 for (i = 0; i < 256; ++i)
893 crtc_state->savePalette[i] = REG_READ(paletteReg + (i << 2));
894}
895
896/**
897 * Restore HW states of giving crtc
898 */
899static void psb_intel_crtc_restore(struct drm_crtc *crtc)
900{
901 struct drm_device *dev = crtc->dev;
902 /* struct drm_psb_private * dev_priv =
903 (struct drm_psb_private *)dev->dev_private; */
904 struct psb_intel_crtc *psb_intel_crtc = to_psb_intel_crtc(crtc);
905 struct psb_intel_crtc_state *crtc_state = psb_intel_crtc->crtc_state;
906 /* struct drm_crtc_helper_funcs * crtc_funcs = crtc->helper_private; */
907 int pipeA = (psb_intel_crtc->pipe == 0);
908 uint32_t paletteReg;
909 int i;
910
911 if (!crtc_state) {
912 dev_err(dev->dev, "No crtc state\n");
913 return;
914 }
915
916 if (crtc_state->saveDPLL & DPLL_VCO_ENABLE) {
917 REG_WRITE(pipeA ? DPLL_A : DPLL_B,
918 crtc_state->saveDPLL & ~DPLL_VCO_ENABLE);
919 REG_READ(pipeA ? DPLL_A : DPLL_B);
920 udelay(150);
921 }
922
923 REG_WRITE(pipeA ? FPA0 : FPB0, crtc_state->saveFP0);
924 REG_READ(pipeA ? FPA0 : FPB0);
925
926 REG_WRITE(pipeA ? FPA1 : FPB1, crtc_state->saveFP1);
927 REG_READ(pipeA ? FPA1 : FPB1);
928
929 REG_WRITE(pipeA ? DPLL_A : DPLL_B, crtc_state->saveDPLL);
930 REG_READ(pipeA ? DPLL_A : DPLL_B);
931 udelay(150);
932
933 REG_WRITE(pipeA ? HTOTAL_A : HTOTAL_B, crtc_state->saveHTOTAL);
934 REG_WRITE(pipeA ? HBLANK_A : HBLANK_B, crtc_state->saveHBLANK);
935 REG_WRITE(pipeA ? HSYNC_A : HSYNC_B, crtc_state->saveHSYNC);
936 REG_WRITE(pipeA ? VTOTAL_A : VTOTAL_B, crtc_state->saveVTOTAL);
937 REG_WRITE(pipeA ? VBLANK_A : VBLANK_B, crtc_state->saveVBLANK);
938 REG_WRITE(pipeA ? VSYNC_A : VSYNC_B, crtc_state->saveVSYNC);
939 REG_WRITE(pipeA ? DSPASTRIDE : DSPBSTRIDE, crtc_state->saveDSPSTRIDE);
940
941 REG_WRITE(pipeA ? DSPASIZE : DSPBSIZE, crtc_state->saveDSPSIZE);
942 REG_WRITE(pipeA ? DSPAPOS : DSPBPOS, crtc_state->saveDSPPOS);
943
944 REG_WRITE(pipeA ? PIPEASRC : PIPEBSRC, crtc_state->savePIPESRC);
945 REG_WRITE(pipeA ? DSPABASE : DSPBBASE, crtc_state->saveDSPBASE);
946 REG_WRITE(pipeA ? PIPEACONF : PIPEBCONF, crtc_state->savePIPECONF);
947
948 psb_intel_wait_for_vblank(dev);
949
950 REG_WRITE(pipeA ? DSPACNTR : DSPBCNTR, crtc_state->saveDSPCNTR);
951 REG_WRITE(pipeA ? DSPABASE : DSPBBASE, crtc_state->saveDSPBASE);
952
953 psb_intel_wait_for_vblank(dev);
954
955 paletteReg = pipeA ? PALETTE_A : PALETTE_B;
956 for (i = 0; i < 256; ++i)
957 REG_WRITE(paletteReg + (i << 2), crtc_state->savePalette[i]);
958}
959
960static int psb_intel_crtc_cursor_set(struct drm_crtc *crtc,
961 struct drm_file *file_priv,
962 uint32_t handle,
963 uint32_t width, uint32_t height)
964{
965 struct drm_device *dev = crtc->dev;
966 struct psb_intel_crtc *psb_intel_crtc = to_psb_intel_crtc(crtc);
967 int pipe = psb_intel_crtc->pipe;
968 uint32_t control = (pipe == 0) ? CURACNTR : CURBCNTR;
969 uint32_t base = (pipe == 0) ? CURABASE : CURBBASE;
970 uint32_t temp;
971 size_t addr = 0;
972 struct gtt_range *gt;
973 struct drm_gem_object *obj;
974 int ret;
975
976 /* if we want to turn of the cursor ignore width and height */
977 if (!handle) {
978 /* turn off the cursor */
979 temp = CURSOR_MODE_DISABLE;
980
981 if (gma_power_begin(dev, false)) {
982 REG_WRITE(control, temp);
983 REG_WRITE(base, 0);
984 gma_power_end(dev);
985 }
986
987 /* Unpin the old GEM object */
988 if (psb_intel_crtc->cursor_obj) {
989 gt = container_of(psb_intel_crtc->cursor_obj,
990 struct gtt_range, gem);
991 psb_gtt_unpin(gt);
992 drm_gem_object_unreference(psb_intel_crtc->cursor_obj);
993 psb_intel_crtc->cursor_obj = NULL;
994 }
995
996 return 0;
997 }
998
999 /* Currently we only support 64x64 cursors */
1000 if (width != 64 || height != 64) {
1001 dev_dbg(dev->dev, "we currently only support 64x64 cursors\n");
1002 return -EINVAL;
1003 }
1004
1005 obj = drm_gem_object_lookup(dev, file_priv, handle);
1006 if (!obj)
1007 return -ENOENT;
1008
1009 if (obj->size < width * height * 4) {
1010 dev_dbg(dev->dev, "buffer is to small\n");
1011 return -ENOMEM;
1012 }
1013
1014 gt = container_of(obj, struct gtt_range, gem);
1015
1016 /* Pin the memory into the GTT */
1017 ret = psb_gtt_pin(gt);
1018 if (ret) {
1019 dev_err(dev->dev, "Can not pin down handle 0x%x\n", handle);
1020 return ret;
1021 }
1022
1023
1024 addr = gt->offset; /* Or resource.start ??? */
1025
1026 psb_intel_crtc->cursor_addr = addr;
1027
1028 temp = 0;
1029 /* set the pipe for the cursor */
1030 temp |= (pipe << 28);
1031 temp |= CURSOR_MODE_64_ARGB_AX | MCURSOR_GAMMA_ENABLE;
1032
1033 if (gma_power_begin(dev, false)) {
1034 REG_WRITE(control, temp);
1035 REG_WRITE(base, addr);
1036 gma_power_end(dev);
1037 }
1038
1039 /* unpin the old bo */
1040 if (psb_intel_crtc->cursor_obj) {
1041 gt = container_of(psb_intel_crtc->cursor_obj,
1042 struct gtt_range, gem);
1043 psb_gtt_unpin(gt);
1044 drm_gem_object_unreference(psb_intel_crtc->cursor_obj);
1045 psb_intel_crtc->cursor_obj = obj;
1046 }
1047 return 0;
1048}
1049
1050static int psb_intel_crtc_cursor_move(struct drm_crtc *crtc, int x, int y)
1051{
1052 struct drm_device *dev = crtc->dev;
1053 struct psb_intel_crtc *psb_intel_crtc = to_psb_intel_crtc(crtc);
1054 int pipe = psb_intel_crtc->pipe;
1055 uint32_t temp = 0;
1056 uint32_t addr;
1057
1058
1059 if (x < 0) {
1060 temp |= (CURSOR_POS_SIGN << CURSOR_X_SHIFT);
1061 x = -x;
1062 }
1063 if (y < 0) {
1064 temp |= (CURSOR_POS_SIGN << CURSOR_Y_SHIFT);
1065 y = -y;
1066 }
1067
1068 temp |= ((x & CURSOR_POS_MASK) << CURSOR_X_SHIFT);
1069 temp |= ((y & CURSOR_POS_MASK) << CURSOR_Y_SHIFT);
1070
1071 addr = psb_intel_crtc->cursor_addr;
1072
1073 if (gma_power_begin(dev, false)) {
1074 REG_WRITE((pipe == 0) ? CURAPOS : CURBPOS, temp);
1075 REG_WRITE((pipe == 0) ? CURABASE : CURBBASE, addr);
1076 gma_power_end(dev);
1077 }
1078 return 0;
1079}
1080
1081void psb_intel_crtc_gamma_set(struct drm_crtc *crtc, u16 *red,
1082 u16 *green, u16 *blue, uint32_t type, uint32_t size)
1083{
1084 struct psb_intel_crtc *psb_intel_crtc = to_psb_intel_crtc(crtc);
1085 int i;
1086
1087 if (size != 256)
1088 return;
1089
1090 for (i = 0; i < 256; i++) {
1091 psb_intel_crtc->lut_r[i] = red[i] >> 8;
1092 psb_intel_crtc->lut_g[i] = green[i] >> 8;
1093 psb_intel_crtc->lut_b[i] = blue[i] >> 8;
1094 }
1095
1096 psb_intel_crtc_load_lut(crtc);
1097}
1098
1099static int psb_crtc_set_config(struct drm_mode_set *set)
1100{
1101 int ret;
1102 struct drm_device *dev = set->crtc->dev;
1103 struct drm_psb_private *dev_priv = dev->dev_private;
1104
1105 if (!dev_priv->rpm_enabled)
1106 return drm_crtc_helper_set_config(set);
1107
1108 pm_runtime_forbid(&dev->pdev->dev);
1109 ret = drm_crtc_helper_set_config(set);
1110 pm_runtime_allow(&dev->pdev->dev);
1111 return ret;
1112}
1113
1114/* Returns the clock of the currently programmed mode of the given pipe. */
1115static int psb_intel_crtc_clock_get(struct drm_device *dev,
1116 struct drm_crtc *crtc)
1117{
1118 struct psb_intel_crtc *psb_intel_crtc = to_psb_intel_crtc(crtc);
1119 int pipe = psb_intel_crtc->pipe;
1120 u32 dpll;
1121 u32 fp;
1122 struct psb_intel_clock_t clock;
1123 bool is_lvds;
1124 struct drm_psb_private *dev_priv = dev->dev_private;
1125
1126 if (gma_power_begin(dev, false)) {
1127 dpll = REG_READ((pipe == 0) ? DPLL_A : DPLL_B);
1128 if ((dpll & DISPLAY_RATE_SELECT_FPA1) == 0)
1129 fp = REG_READ((pipe == 0) ? FPA0 : FPB0);
1130 else
1131 fp = REG_READ((pipe == 0) ? FPA1 : FPB1);
1132 is_lvds = (pipe == 1) && (REG_READ(LVDS) & LVDS_PORT_EN);
1133 gma_power_end(dev);
1134 } else {
1135 dpll = (pipe == 0) ?
1136 dev_priv->saveDPLL_A : dev_priv->saveDPLL_B;
1137
1138 if ((dpll & DISPLAY_RATE_SELECT_FPA1) == 0)
1139 fp = (pipe == 0) ?
1140 dev_priv->saveFPA0 :
1141 dev_priv->saveFPB0;
1142 else
1143 fp = (pipe == 0) ?
1144 dev_priv->saveFPA1 :
1145 dev_priv->saveFPB1;
1146
1147 is_lvds = (pipe == 1) && (dev_priv->saveLVDS & LVDS_PORT_EN);
1148 }
1149
1150 clock.m1 = (fp & FP_M1_DIV_MASK) >> FP_M1_DIV_SHIFT;
1151 clock.m2 = (fp & FP_M2_DIV_MASK) >> FP_M2_DIV_SHIFT;
1152 clock.n = (fp & FP_N_DIV_MASK) >> FP_N_DIV_SHIFT;
1153
1154 if (is_lvds) {
1155 clock.p1 =
1156 ffs((dpll &
1157 DPLL_FPA01_P1_POST_DIV_MASK_I830_LVDS) >>
1158 DPLL_FPA01_P1_POST_DIV_SHIFT);
1159 clock.p2 = 14;
1160
1161 if ((dpll & PLL_REF_INPUT_MASK) ==
1162 PLLB_REF_INPUT_SPREADSPECTRUMIN) {
1163 /* XXX: might not be 66MHz */
1164 i8xx_clock(66000, &clock);
1165 } else
1166 i8xx_clock(48000, &clock);
1167 } else {
1168 if (dpll & PLL_P1_DIVIDE_BY_TWO)
1169 clock.p1 = 2;
1170 else {
1171 clock.p1 =
1172 ((dpll &
1173 DPLL_FPA01_P1_POST_DIV_MASK_I830) >>
1174 DPLL_FPA01_P1_POST_DIV_SHIFT) + 2;
1175 }
1176 if (dpll & PLL_P2_DIVIDE_BY_4)
1177 clock.p2 = 4;
1178 else
1179 clock.p2 = 2;
1180
1181 i8xx_clock(48000, &clock);
1182 }
1183
1184 /* XXX: It would be nice to validate the clocks, but we can't reuse
1185 * i830PllIsValid() because it relies on the xf86_config connector
1186 * configuration being accurate, which it isn't necessarily.
1187 */
1188
1189 return clock.dot;
1190}
1191
1192/** Returns the currently programmed mode of the given pipe. */
1193struct drm_display_mode *psb_intel_crtc_mode_get(struct drm_device *dev,
1194 struct drm_crtc *crtc)
1195{
1196 struct psb_intel_crtc *psb_intel_crtc = to_psb_intel_crtc(crtc);
1197 int pipe = psb_intel_crtc->pipe;
1198 struct drm_display_mode *mode;
1199 int htot;
1200 int hsync;
1201 int vtot;
1202 int vsync;
1203 struct drm_psb_private *dev_priv = dev->dev_private;
1204
1205 if (gma_power_begin(dev, false)) {
1206 htot = REG_READ((pipe == 0) ? HTOTAL_A : HTOTAL_B);
1207 hsync = REG_READ((pipe == 0) ? HSYNC_A : HSYNC_B);
1208 vtot = REG_READ((pipe == 0) ? VTOTAL_A : VTOTAL_B);
1209 vsync = REG_READ((pipe == 0) ? VSYNC_A : VSYNC_B);
1210 gma_power_end(dev);
1211 } else {
1212 htot = (pipe == 0) ?
1213 dev_priv->saveHTOTAL_A : dev_priv->saveHTOTAL_B;
1214 hsync = (pipe == 0) ?
1215 dev_priv->saveHSYNC_A : dev_priv->saveHSYNC_B;
1216 vtot = (pipe == 0) ?
1217 dev_priv->saveVTOTAL_A : dev_priv->saveVTOTAL_B;
1218 vsync = (pipe == 0) ?
1219 dev_priv->saveVSYNC_A : dev_priv->saveVSYNC_B;
1220 }
1221
1222 mode = kzalloc(sizeof(*mode), GFP_KERNEL);
1223 if (!mode)
1224 return NULL;
1225
1226 mode->clock = psb_intel_crtc_clock_get(dev, crtc);
1227 mode->hdisplay = (htot & 0xffff) + 1;
1228 mode->htotal = ((htot & 0xffff0000) >> 16) + 1;
1229 mode->hsync_start = (hsync & 0xffff) + 1;
1230 mode->hsync_end = ((hsync & 0xffff0000) >> 16) + 1;
1231 mode->vdisplay = (vtot & 0xffff) + 1;
1232 mode->vtotal = ((vtot & 0xffff0000) >> 16) + 1;
1233 mode->vsync_start = (vsync & 0xffff) + 1;
1234 mode->vsync_end = ((vsync & 0xffff0000) >> 16) + 1;
1235
1236 drm_mode_set_name(mode);
1237 drm_mode_set_crtcinfo(mode, 0);
1238
1239 return mode;
1240}
1241
1242void psb_intel_crtc_destroy(struct drm_crtc *crtc)
1243{
1244 struct psb_intel_crtc *psb_intel_crtc = to_psb_intel_crtc(crtc);
1245 struct gtt_range *gt;
1246
1247 /* Unpin the old GEM object */
1248 if (psb_intel_crtc->cursor_obj) {
1249 gt = container_of(psb_intel_crtc->cursor_obj,
1250 struct gtt_range, gem);
1251 psb_gtt_unpin(gt);
1252 drm_gem_object_unreference(psb_intel_crtc->cursor_obj);
1253 psb_intel_crtc->cursor_obj = NULL;
1254 }
1255 kfree(psb_intel_crtc->crtc_state);
1256 drm_crtc_cleanup(crtc);
1257 kfree(psb_intel_crtc);
1258}
1259
1260const struct drm_crtc_helper_funcs psb_intel_helper_funcs = {
1261 .dpms = psb_intel_crtc_dpms,
1262 .mode_fixup = psb_intel_crtc_mode_fixup,
1263 .mode_set = psb_intel_crtc_mode_set,
1264 .mode_set_base = psb_intel_pipe_set_base,
1265 .prepare = psb_intel_crtc_prepare,
1266 .commit = psb_intel_crtc_commit,
1267};
1268
1269const struct drm_crtc_funcs psb_intel_crtc_funcs = {
1270 .save = psb_intel_crtc_save,
1271 .restore = psb_intel_crtc_restore,
1272 .cursor_set = psb_intel_crtc_cursor_set,
1273 .cursor_move = psb_intel_crtc_cursor_move,
1274 .gamma_set = psb_intel_crtc_gamma_set,
1275 .set_config = psb_crtc_set_config,
1276 .destroy = psb_intel_crtc_destroy,
1277};
1278
1279/*
1280 * Set the default value of cursor control and base register
1281 * to zero. This is a workaround for h/w defect on Oaktrail
1282 */
1283static void psb_intel_cursor_init(struct drm_device *dev, int pipe)
1284{
1285 u32 control[3] = { CURACNTR, CURBCNTR, CURCCNTR };
1286 u32 base[3] = { CURABASE, CURBBASE, CURCBASE };
1287
1288 REG_WRITE(control[pipe], 0);
1289 REG_WRITE(base[pipe], 0);
1290}
1291
1292void psb_intel_crtc_init(struct drm_device *dev, int pipe,
1293 struct psb_intel_mode_device *mode_dev)
1294{
1295 struct drm_psb_private *dev_priv = dev->dev_private;
1296 struct psb_intel_crtc *psb_intel_crtc;
1297 int i;
1298 uint16_t *r_base, *g_base, *b_base;
1299
1300 /* We allocate a extra array of drm_connector pointers
1301 * for fbdev after the crtc */
1302 psb_intel_crtc =
1303 kzalloc(sizeof(struct psb_intel_crtc) +
1304 (INTELFB_CONN_LIMIT * sizeof(struct drm_connector *)),
1305 GFP_KERNEL);
1306 if (psb_intel_crtc == NULL)
1307 return;
1308
1309 psb_intel_crtc->crtc_state =
1310 kzalloc(sizeof(struct psb_intel_crtc_state), GFP_KERNEL);
1311 if (!psb_intel_crtc->crtc_state) {
1312 dev_err(dev->dev, "Crtc state error: No memory\n");
1313 kfree(psb_intel_crtc);
1314 return;
1315 }
1316
1317 /* Set the CRTC operations from the chip specific data */
1318 drm_crtc_init(dev, &psb_intel_crtc->base, dev_priv->ops->crtc_funcs);
1319
1320 drm_mode_crtc_set_gamma_size(&psb_intel_crtc->base, 256);
1321 psb_intel_crtc->pipe = pipe;
1322 psb_intel_crtc->plane = pipe;
1323
1324 r_base = psb_intel_crtc->base.gamma_store;
1325 g_base = r_base + 256;
1326 b_base = g_base + 256;
1327 for (i = 0; i < 256; i++) {
1328 psb_intel_crtc->lut_r[i] = i;
1329 psb_intel_crtc->lut_g[i] = i;
1330 psb_intel_crtc->lut_b[i] = i;
1331 r_base[i] = i << 8;
1332 g_base[i] = i << 8;
1333 b_base[i] = i << 8;
1334
1335 psb_intel_crtc->lut_adj[i] = 0;
1336 }
1337
1338 psb_intel_crtc->mode_dev = mode_dev;
1339 psb_intel_crtc->cursor_addr = 0;
1340
1341 drm_crtc_helper_add(&psb_intel_crtc->base,
1342 dev_priv->ops->crtc_helper);
1343
1344 /* Setup the array of drm_connector pointer array */
1345 psb_intel_crtc->mode_set.crtc = &psb_intel_crtc->base;
1346 BUG_ON(pipe >= ARRAY_SIZE(dev_priv->plane_to_crtc_mapping) ||
1347 dev_priv->plane_to_crtc_mapping[psb_intel_crtc->plane] != NULL);
1348 dev_priv->plane_to_crtc_mapping[psb_intel_crtc->plane] =
1349 &psb_intel_crtc->base;
1350 dev_priv->pipe_to_crtc_mapping[psb_intel_crtc->pipe] =
1351 &psb_intel_crtc->base;
1352 psb_intel_crtc->mode_set.connectors =
1353 (struct drm_connector **) (psb_intel_crtc + 1);
1354 psb_intel_crtc->mode_set.num_connectors = 0;
1355 psb_intel_cursor_init(dev, pipe);
1356}
1357
1358int psb_intel_get_pipe_from_crtc_id(struct drm_device *dev, void *data,
1359 struct drm_file *file_priv)
1360{
1361 struct drm_psb_private *dev_priv = dev->dev_private;
1362 struct drm_psb_get_pipe_from_crtc_id_arg *pipe_from_crtc_id = data;
1363 struct drm_mode_object *drmmode_obj;
1364 struct psb_intel_crtc *crtc;
1365
1366 if (!dev_priv) {
1367 dev_err(dev->dev, "called with no initialization\n");
1368 return -EINVAL;
1369 }
1370
1371 drmmode_obj = drm_mode_object_find(dev, pipe_from_crtc_id->crtc_id,
1372 DRM_MODE_OBJECT_CRTC);
1373
1374 if (!drmmode_obj) {
1375 dev_err(dev->dev, "no such CRTC id\n");
1376 return -EINVAL;
1377 }
1378
1379 crtc = to_psb_intel_crtc(obj_to_crtc(drmmode_obj));
1380 pipe_from_crtc_id->pipe = crtc->pipe;
1381
1382 return 0;
1383}
1384
1385struct drm_crtc *psb_intel_get_crtc_from_pipe(struct drm_device *dev, int pipe)
1386{
1387 struct drm_crtc *crtc = NULL;
1388
1389 list_for_each_entry(crtc, &dev->mode_config.crtc_list, head) {
1390 struct psb_intel_crtc *psb_intel_crtc = to_psb_intel_crtc(crtc);
1391 if (psb_intel_crtc->pipe == pipe)
1392 break;
1393 }
1394 return crtc;
1395}
1396
1397int psb_intel_connector_clones(struct drm_device *dev, int type_mask)
1398{
1399 int index_mask = 0;
1400 struct drm_connector *connector;
1401 int entry = 0;
1402
1403 list_for_each_entry(connector, &dev->mode_config.connector_list,
1404 head) {
1405 struct psb_intel_output *psb_intel_output =
1406 to_psb_intel_output(connector);
1407 if (type_mask & (1 << psb_intel_output->type))
1408 index_mask |= (1 << entry);
1409 entry++;
1410 }
1411 return index_mask;
1412}
1413
1414
1415void psb_intel_modeset_cleanup(struct drm_device *dev)
1416{
1417 drm_mode_config_cleanup(dev);
1418}
1419
1420
1421/* current intel driver doesn't take advantage of encoders
1422 always give back the encoder for the connector
1423*/
1424struct drm_encoder *psb_intel_best_encoder(struct drm_connector *connector)
1425{
1426 struct psb_intel_output *psb_intel_output =
1427 to_psb_intel_output(connector);
1428
1429 return &psb_intel_output->enc;
1430}
1431
diff --git a/drivers/gpu/drm/gma500/psb_intel_display.h b/drivers/gpu/drm/gma500/psb_intel_display.h
new file mode 100644
index 000000000000..535b49a5e409
--- /dev/null
+++ b/drivers/gpu/drm/gma500/psb_intel_display.h
@@ -0,0 +1,28 @@
1/* copyright (c) 2008, Intel Corporation
2 *
3 * This program is free software; you can redistribute it and/or modify it
4 * under the terms and conditions of the GNU General Public License,
5 * version 2, as published by the Free Software Foundation.
6 *
7 * This program is distributed in the hope it will be useful, but WITHOUT
8 * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
9 * FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for
10 * more details.
11 *
12 * You should have received a copy of the GNU General Public License along with
13 * this program; if not, write to the Free Software Foundation, Inc.,
14 * 51 Franklin St - Fifth Floor, Boston, MA 02110-1301 USA.
15 *
16 * Authors:
17 * Eric Anholt <eric@anholt.net>
18 */
19
20#ifndef _INTEL_DISPLAY_H_
21#define _INTEL_DISPLAY_H_
22
23bool psb_intel_pipe_has_type(struct drm_crtc *crtc, int type);
24void psb_intel_crtc_gamma_set(struct drm_crtc *crtc, u16 *red,
25 u16 *green, u16 *blue, uint32_t type, uint32_t size);
26void psb_intel_crtc_destroy(struct drm_crtc *crtc);
27
28#endif
diff --git a/drivers/gpu/drm/gma500/psb_intel_drv.h b/drivers/gpu/drm/gma500/psb_intel_drv.h
new file mode 100644
index 000000000000..ac953ca430a8
--- /dev/null
+++ b/drivers/gpu/drm/gma500/psb_intel_drv.h
@@ -0,0 +1,228 @@
1/*
2 * Copyright (c) 2009-2011, Intel Corporation.
3 *
4 * This program is free software; you can redistribute it and/or modify it
5 * under the terms and conditions of the GNU General Public License,
6 * version 2, as published by the Free Software Foundation.
7 *
8 * This program is distributed in the hope it will be useful, but WITHOUT
9 * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
10 * FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for
11 * more details.
12 *
13 * You should have received a copy of the GNU General Public License along with
14 * this program; if not, write to the Free Software Foundation, Inc.,
15 * 51 Franklin St - Fifth Floor, Boston, MA 02110-1301 USA.
16 *
17 */
18
19#ifndef __INTEL_DRV_H__
20#define __INTEL_DRV_H__
21
22#include <linux/i2c.h>
23#include <linux/i2c-algo-bit.h>
24#include <drm/drm_crtc.h>
25#include <drm/drm_crtc_helper.h>
26#include <linux/gpio.h>
27
28/*
29 * Display related stuff
30 */
31
32/* store information about an Ixxx DVO */
33/* The i830->i865 use multiple DVOs with multiple i2cs */
34/* the i915, i945 have a single sDVO i2c bus - which is different */
35#define MAX_OUTPUTS 6
36/* maximum connectors per crtcs in the mode set */
37#define INTELFB_CONN_LIMIT 4
38
39#define INTEL_I2C_BUS_DVO 1
40#define INTEL_I2C_BUS_SDVO 2
41
42/* these are outputs from the chip - integrated only
43 * external chips are via DVO or SDVO output */
44#define INTEL_OUTPUT_UNUSED 0
45#define INTEL_OUTPUT_ANALOG 1
46#define INTEL_OUTPUT_DVO 2
47#define INTEL_OUTPUT_SDVO 3
48#define INTEL_OUTPUT_LVDS 4
49#define INTEL_OUTPUT_TVOUT 5
50#define INTEL_OUTPUT_HDMI 6
51#define INTEL_OUTPUT_MIPI 7
52#define INTEL_OUTPUT_MIPI2 8
53
54#define INTEL_DVO_CHIP_NONE 0
55#define INTEL_DVO_CHIP_LVDS 1
56#define INTEL_DVO_CHIP_TMDS 2
57#define INTEL_DVO_CHIP_TVOUT 4
58
59/*
60 * Hold information useally put on the device driver privates here,
61 * since it needs to be shared across multiple of devices drivers privates.
62 */
63struct psb_intel_mode_device {
64
65 /*
66 * Abstracted memory manager operations
67 */
68 size_t(*bo_offset) (struct drm_device *dev, void *bo);
69
70 /*
71 * Cursor (Can go ?)
72 */
73 int cursor_needs_physical;
74
75 /*
76 * LVDS info
77 */
78 int backlight_duty_cycle; /* restore backlight to this value */
79 bool panel_wants_dither;
80 struct drm_display_mode *panel_fixed_mode;
81 struct drm_display_mode *panel_fixed_mode2;
82 struct drm_display_mode *vbt_mode; /* if any */
83
84 uint32_t saveBLC_PWM_CTL;
85};
86
87struct psb_intel_i2c_chan {
88 /* for getting at dev. private (mmio etc.) */
89 struct drm_device *drm_dev;
90 u32 reg; /* GPIO reg */
91 struct i2c_adapter adapter;
92 struct i2c_algo_bit_data algo;
93 u8 slave_addr;
94};
95
96struct psb_intel_output {
97 struct drm_connector base;
98
99 struct drm_encoder enc;
100 int type;
101
102 struct psb_intel_i2c_chan *i2c_bus; /* for control functions */
103 struct psb_intel_i2c_chan *ddc_bus; /* for DDC only stuff */
104 bool load_detect_temp;
105 void *dev_priv;
106
107 struct psb_intel_mode_device *mode_dev;
108 struct i2c_adapter *hdmi_i2c_adapter; /* for control functions */
109};
110
111struct psb_intel_crtc_state {
112 uint32_t saveDSPCNTR;
113 uint32_t savePIPECONF;
114 uint32_t savePIPESRC;
115 uint32_t saveDPLL;
116 uint32_t saveFP0;
117 uint32_t saveFP1;
118 uint32_t saveHTOTAL;
119 uint32_t saveHBLANK;
120 uint32_t saveHSYNC;
121 uint32_t saveVTOTAL;
122 uint32_t saveVBLANK;
123 uint32_t saveVSYNC;
124 uint32_t saveDSPSTRIDE;
125 uint32_t saveDSPSIZE;
126 uint32_t saveDSPPOS;
127 uint32_t saveDSPBASE;
128 uint32_t savePalette[256];
129};
130
131struct psb_intel_crtc {
132 struct drm_crtc base;
133 int pipe;
134 int plane;
135 uint32_t cursor_addr;
136 u8 lut_r[256], lut_g[256], lut_b[256];
137 u8 lut_adj[256];
138 struct psb_intel_framebuffer *fbdev_fb;
139 /* a mode_set for fbdev users on this crtc */
140 struct drm_mode_set mode_set;
141
142 /* GEM object that holds our cursor */
143 struct drm_gem_object *cursor_obj;
144
145 struct drm_display_mode saved_mode;
146 struct drm_display_mode saved_adjusted_mode;
147
148 struct psb_intel_mode_device *mode_dev;
149
150 /*crtc mode setting flags*/
151 u32 mode_flags;
152
153 /* Saved Crtc HW states */
154 struct psb_intel_crtc_state *crtc_state;
155};
156
157#define to_psb_intel_crtc(x) \
158 container_of(x, struct psb_intel_crtc, base)
159#define to_psb_intel_output(x) \
160 container_of(x, struct psb_intel_output, base)
161#define enc_to_psb_intel_output(x) \
162 container_of(x, struct psb_intel_output, enc)
163#define to_psb_intel_framebuffer(x) \
164 container_of(x, struct psb_intel_framebuffer, base)
165
166struct psb_intel_i2c_chan *psb_intel_i2c_create(struct drm_device *dev,
167 const u32 reg, const char *name);
168void psb_intel_i2c_destroy(struct psb_intel_i2c_chan *chan);
169int psb_intel_ddc_get_modes(struct psb_intel_output *psb_intel_output);
170extern bool psb_intel_ddc_probe(struct psb_intel_output *psb_intel_output);
171
172extern void psb_intel_crtc_init(struct drm_device *dev, int pipe,
173 struct psb_intel_mode_device *mode_dev);
174extern void psb_intel_crt_init(struct drm_device *dev);
175extern void psb_intel_sdvo_init(struct drm_device *dev, int output_device);
176extern void psb_intel_dvo_init(struct drm_device *dev);
177extern void psb_intel_tv_init(struct drm_device *dev);
178extern void psb_intel_lvds_init(struct drm_device *dev,
179 struct psb_intel_mode_device *mode_dev);
180extern void psb_intel_lvds_set_brightness(struct drm_device *dev, int level);
181extern void oaktrail_lvds_init(struct drm_device *dev,
182 struct psb_intel_mode_device *mode_dev);
183extern void oaktrail_wait_for_INTR_PKT_SENT(struct drm_device *dev);
184extern void oaktrail_dsi_init(struct drm_device *dev,
185 struct psb_intel_mode_device *mode_dev);
186extern void mid_dsi_init(struct drm_device *dev,
187 struct psb_intel_mode_device *mode_dev, int dsi_num);
188
189extern void psb_intel_crtc_load_lut(struct drm_crtc *crtc);
190extern void psb_intel_encoder_prepare(struct drm_encoder *encoder);
191extern void psb_intel_encoder_commit(struct drm_encoder *encoder);
192
193extern struct drm_encoder *psb_intel_best_encoder(struct drm_connector
194 *connector);
195
196extern struct drm_display_mode *psb_intel_crtc_mode_get(struct drm_device *dev,
197 struct drm_crtc *crtc);
198extern void psb_intel_wait_for_vblank(struct drm_device *dev);
199extern int psb_intel_get_pipe_from_crtc_id(struct drm_device *dev, void *data,
200 struct drm_file *file_priv);
201extern struct drm_crtc *psb_intel_get_crtc_from_pipe(struct drm_device *dev,
202 int pipe);
203extern struct drm_connector *psb_intel_sdvo_find(struct drm_device *dev,
204 int sdvoB);
205extern int psb_intel_sdvo_supports_hotplug(struct drm_connector *connector);
206extern void psb_intel_sdvo_set_hotplug(struct drm_connector *connector,
207 int enable);
208extern int intelfb_probe(struct drm_device *dev);
209extern int intelfb_remove(struct drm_device *dev,
210 struct drm_framebuffer *fb);
211extern struct drm_framebuffer *psb_intel_framebuffer_create(struct drm_device
212 *dev, struct
213 drm_mode_fb_cmd
214 *mode_cmd,
215 void *mm_private);
216extern bool psb_intel_lvds_mode_fixup(struct drm_encoder *encoder,
217 struct drm_display_mode *mode,
218 struct drm_display_mode *adjusted_mode);
219extern int psb_intel_lvds_mode_valid(struct drm_connector *connector,
220 struct drm_display_mode *mode);
221extern int psb_intel_lvds_set_property(struct drm_connector *connector,
222 struct drm_property *property,
223 uint64_t value);
224extern void psb_intel_lvds_destroy(struct drm_connector *connector);
225extern const struct drm_encoder_funcs psb_intel_lvds_enc_funcs;
226
227
228#endif /* __INTEL_DRV_H__ */
diff --git a/drivers/gpu/drm/gma500/psb_intel_lvds.c b/drivers/gpu/drm/gma500/psb_intel_lvds.c
new file mode 100644
index 000000000000..c6436da60732
--- /dev/null
+++ b/drivers/gpu/drm/gma500/psb_intel_lvds.c
@@ -0,0 +1,849 @@
1/*
2 * Copyright © 2006-2007 Intel Corporation
3 *
4 * This program is free software; you can redistribute it and/or modify it
5 * under the terms and conditions of the GNU General Public License,
6 * version 2, as published by the Free Software Foundation.
7 *
8 * This program is distributed in the hope it will be useful, but WITHOUT
9 * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
10 * FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for
11 * more details.
12 *
13 * You should have received a copy of the GNU General Public License along with
14 * this program; if not, write to the Free Software Foundation, Inc.,
15 * 51 Franklin St - Fifth Floor, Boston, MA 02110-1301 USA.
16 *
17 * Authors:
18 * Eric Anholt <eric@anholt.net>
19 * Dave Airlie <airlied@linux.ie>
20 * Jesse Barnes <jesse.barnes@intel.com>
21 */
22
23#include <linux/i2c.h>
24#include <drm/drmP.h>
25
26#include "intel_bios.h"
27#include "psb_drv.h"
28#include "psb_intel_drv.h"
29#include "psb_intel_reg.h"
30#include "power.h"
31#include <linux/pm_runtime.h>
32
33/*
34 * LVDS I2C backlight control macros
35 */
36#define BRIGHTNESS_MAX_LEVEL 100
37#define BRIGHTNESS_MASK 0xFF
38#define BLC_I2C_TYPE 0x01
39#define BLC_PWM_TYPT 0x02
40
41#define BLC_POLARITY_NORMAL 0
42#define BLC_POLARITY_INVERSE 1
43
44#define PSB_BLC_MAX_PWM_REG_FREQ (0xFFFE)
45#define PSB_BLC_MIN_PWM_REG_FREQ (0x2)
46#define PSB_BLC_PWM_PRECISION_FACTOR (10)
47#define PSB_BACKLIGHT_PWM_CTL_SHIFT (16)
48#define PSB_BACKLIGHT_PWM_POLARITY_BIT_CLEAR (0xFFFE)
49
50struct psb_intel_lvds_priv {
51 /*
52 * Saved LVDO output states
53 */
54 uint32_t savePP_ON;
55 uint32_t savePP_OFF;
56 uint32_t saveLVDS;
57 uint32_t savePP_CONTROL;
58 uint32_t savePP_CYCLE;
59 uint32_t savePFIT_CONTROL;
60 uint32_t savePFIT_PGM_RATIOS;
61 uint32_t saveBLC_PWM_CTL;
62};
63
64
65/*
66 * Returns the maximum level of the backlight duty cycle field.
67 */
68static u32 psb_intel_lvds_get_max_backlight(struct drm_device *dev)
69{
70 struct drm_psb_private *dev_priv = dev->dev_private;
71 u32 retVal;
72
73 if (gma_power_begin(dev, false)) {
74 retVal = ((REG_READ(BLC_PWM_CTL) &
75 BACKLIGHT_MODULATION_FREQ_MASK) >>
76 BACKLIGHT_MODULATION_FREQ_SHIFT) * 2;
77
78 gma_power_end(dev);
79 } else
80 retVal = ((dev_priv->saveBLC_PWM_CTL &
81 BACKLIGHT_MODULATION_FREQ_MASK) >>
82 BACKLIGHT_MODULATION_FREQ_SHIFT) * 2;
83
84 return retVal;
85}
86
87/*
88 * Set LVDS backlight level by I2C command
89 *
90 * FIXME: at some point we need to both track this for PM and also
91 * disable runtime pm on MRST if the brightness is nil (ie blanked)
92 */
93static int psb_lvds_i2c_set_brightness(struct drm_device *dev,
94 unsigned int level)
95{
96 struct drm_psb_private *dev_priv =
97 (struct drm_psb_private *)dev->dev_private;
98
99 struct psb_intel_i2c_chan *lvds_i2c_bus = dev_priv->lvds_i2c_bus;
100 u8 out_buf[2];
101 unsigned int blc_i2c_brightness;
102
103 struct i2c_msg msgs[] = {
104 {
105 .addr = lvds_i2c_bus->slave_addr,
106 .flags = 0,
107 .len = 2,
108 .buf = out_buf,
109 }
110 };
111
112 blc_i2c_brightness = BRIGHTNESS_MASK & ((unsigned int)level *
113 BRIGHTNESS_MASK /
114 BRIGHTNESS_MAX_LEVEL);
115
116 if (dev_priv->lvds_bl->pol == BLC_POLARITY_INVERSE)
117 blc_i2c_brightness = BRIGHTNESS_MASK - blc_i2c_brightness;
118
119 out_buf[0] = dev_priv->lvds_bl->brightnesscmd;
120 out_buf[1] = (u8)blc_i2c_brightness;
121
122 if (i2c_transfer(&lvds_i2c_bus->adapter, msgs, 1) == 1) {
123 dev_dbg(dev->dev, "I2C set brightness.(command, value) (%d, %d)\n",
124 dev_priv->lvds_bl->brightnesscmd,
125 blc_i2c_brightness);
126 return 0;
127 }
128
129 dev_err(dev->dev, "I2C transfer error\n");
130 return -1;
131}
132
133
134static int psb_lvds_pwm_set_brightness(struct drm_device *dev, int level)
135{
136 struct drm_psb_private *dev_priv =
137 (struct drm_psb_private *)dev->dev_private;
138
139 u32 max_pwm_blc;
140 u32 blc_pwm_duty_cycle;
141
142 max_pwm_blc = psb_intel_lvds_get_max_backlight(dev);
143
144 /*BLC_PWM_CTL Should be initiated while backlight device init*/
145 BUG_ON((max_pwm_blc & PSB_BLC_MAX_PWM_REG_FREQ) == 0);
146
147 blc_pwm_duty_cycle = level * max_pwm_blc / BRIGHTNESS_MAX_LEVEL;
148
149 if (dev_priv->lvds_bl->pol == BLC_POLARITY_INVERSE)
150 blc_pwm_duty_cycle = max_pwm_blc - blc_pwm_duty_cycle;
151
152 blc_pwm_duty_cycle &= PSB_BACKLIGHT_PWM_POLARITY_BIT_CLEAR;
153 REG_WRITE(BLC_PWM_CTL,
154 (max_pwm_blc << PSB_BACKLIGHT_PWM_CTL_SHIFT) |
155 (blc_pwm_duty_cycle));
156
157 return 0;
158}
159
160/*
161 * Set LVDS backlight level either by I2C or PWM
162 */
163void psb_intel_lvds_set_brightness(struct drm_device *dev, int level)
164{
165 /*u32 blc_pwm_ctl;*/
166 struct drm_psb_private *dev_priv =
167 (struct drm_psb_private *)dev->dev_private;
168
169 dev_dbg(dev->dev, "backlight level is %d\n", level);
170
171 if (!dev_priv->lvds_bl) {
172 dev_err(dev->dev, "NO LVDS Backlight Info\n");
173 return;
174 }
175
176 if (dev_priv->lvds_bl->type == BLC_I2C_TYPE)
177 psb_lvds_i2c_set_brightness(dev, level);
178 else
179 psb_lvds_pwm_set_brightness(dev, level);
180}
181
182/*
183 * Sets the backlight level.
184 *
185 * level: backlight level, from 0 to psb_intel_lvds_get_max_backlight().
186 */
187static void psb_intel_lvds_set_backlight(struct drm_device *dev, int level)
188{
189 struct drm_psb_private *dev_priv = dev->dev_private;
190 u32 blc_pwm_ctl;
191
192 if (gma_power_begin(dev, false)) {
193 blc_pwm_ctl =
194 REG_READ(BLC_PWM_CTL) & ~BACKLIGHT_DUTY_CYCLE_MASK;
195 REG_WRITE(BLC_PWM_CTL,
196 (blc_pwm_ctl |
197 (level << BACKLIGHT_DUTY_CYCLE_SHIFT)));
198 gma_power_end(dev);
199 } else {
200 blc_pwm_ctl = dev_priv->saveBLC_PWM_CTL &
201 ~BACKLIGHT_DUTY_CYCLE_MASK;
202 dev_priv->saveBLC_PWM_CTL = (blc_pwm_ctl |
203 (level << BACKLIGHT_DUTY_CYCLE_SHIFT));
204 }
205}
206
207/*
208 * Sets the power state for the panel.
209 */
210static void psb_intel_lvds_set_power(struct drm_device *dev,
211 struct psb_intel_output *output, bool on)
212{
213 u32 pp_status;
214
215 if (!gma_power_begin(dev, true))
216 return;
217
218 if (on) {
219 REG_WRITE(PP_CONTROL, REG_READ(PP_CONTROL) |
220 POWER_TARGET_ON);
221 do {
222 pp_status = REG_READ(PP_STATUS);
223 } while ((pp_status & PP_ON) == 0);
224
225 psb_intel_lvds_set_backlight(dev,
226 output->
227 mode_dev->backlight_duty_cycle);
228 } else {
229 psb_intel_lvds_set_backlight(dev, 0);
230
231 REG_WRITE(PP_CONTROL, REG_READ(PP_CONTROL) &
232 ~POWER_TARGET_ON);
233 do {
234 pp_status = REG_READ(PP_STATUS);
235 } while (pp_status & PP_ON);
236 }
237
238 gma_power_end(dev);
239}
240
241static void psb_intel_lvds_encoder_dpms(struct drm_encoder *encoder, int mode)
242{
243 struct drm_device *dev = encoder->dev;
244 struct psb_intel_output *output = enc_to_psb_intel_output(encoder);
245
246 if (mode == DRM_MODE_DPMS_ON)
247 psb_intel_lvds_set_power(dev, output, true);
248 else
249 psb_intel_lvds_set_power(dev, output, false);
250
251 /* XXX: We never power down the LVDS pairs. */
252}
253
254static void psb_intel_lvds_save(struct drm_connector *connector)
255{
256 struct drm_device *dev = connector->dev;
257 struct drm_psb_private *dev_priv =
258 (struct drm_psb_private *)dev->dev_private;
259 struct psb_intel_output *psb_intel_output =
260 to_psb_intel_output(connector);
261 struct psb_intel_lvds_priv *lvds_priv =
262 (struct psb_intel_lvds_priv *)psb_intel_output->dev_priv;
263
264 lvds_priv->savePP_ON = REG_READ(LVDSPP_ON);
265 lvds_priv->savePP_OFF = REG_READ(LVDSPP_OFF);
266 lvds_priv->saveLVDS = REG_READ(LVDS);
267 lvds_priv->savePP_CONTROL = REG_READ(PP_CONTROL);
268 lvds_priv->savePP_CYCLE = REG_READ(PP_CYCLE);
269 /*lvds_priv->savePP_DIVISOR = REG_READ(PP_DIVISOR);*/
270 lvds_priv->saveBLC_PWM_CTL = REG_READ(BLC_PWM_CTL);
271 lvds_priv->savePFIT_CONTROL = REG_READ(PFIT_CONTROL);
272 lvds_priv->savePFIT_PGM_RATIOS = REG_READ(PFIT_PGM_RATIOS);
273
274 /*TODO: move backlight_duty_cycle to psb_intel_lvds_priv*/
275 dev_priv->backlight_duty_cycle = (dev_priv->saveBLC_PWM_CTL &
276 BACKLIGHT_DUTY_CYCLE_MASK);
277
278 /*
279 * If the light is off at server startup,
280 * just make it full brightness
281 */
282 if (dev_priv->backlight_duty_cycle == 0)
283 dev_priv->backlight_duty_cycle =
284 psb_intel_lvds_get_max_backlight(dev);
285
286 dev_dbg(dev->dev, "(0x%x, 0x%x, 0x%x, 0x%x, 0x%x, 0x%x)\n",
287 lvds_priv->savePP_ON,
288 lvds_priv->savePP_OFF,
289 lvds_priv->saveLVDS,
290 lvds_priv->savePP_CONTROL,
291 lvds_priv->savePP_CYCLE,
292 lvds_priv->saveBLC_PWM_CTL);
293}
294
295static void psb_intel_lvds_restore(struct drm_connector *connector)
296{
297 struct drm_device *dev = connector->dev;
298 u32 pp_status;
299
300 /*struct drm_psb_private *dev_priv =
301 (struct drm_psb_private *)dev->dev_private;*/
302 struct psb_intel_output *psb_intel_output =
303 to_psb_intel_output(connector);
304 struct psb_intel_lvds_priv *lvds_priv =
305 (struct psb_intel_lvds_priv *)psb_intel_output->dev_priv;
306
307 dev_dbg(dev->dev, "(0x%x, 0x%x, 0x%x, 0x%x, 0x%x, 0x%x)\n",
308 lvds_priv->savePP_ON,
309 lvds_priv->savePP_OFF,
310 lvds_priv->saveLVDS,
311 lvds_priv->savePP_CONTROL,
312 lvds_priv->savePP_CYCLE,
313 lvds_priv->saveBLC_PWM_CTL);
314
315 REG_WRITE(BLC_PWM_CTL, lvds_priv->saveBLC_PWM_CTL);
316 REG_WRITE(PFIT_CONTROL, lvds_priv->savePFIT_CONTROL);
317 REG_WRITE(PFIT_PGM_RATIOS, lvds_priv->savePFIT_PGM_RATIOS);
318 REG_WRITE(LVDSPP_ON, lvds_priv->savePP_ON);
319 REG_WRITE(LVDSPP_OFF, lvds_priv->savePP_OFF);
320 /*REG_WRITE(PP_DIVISOR, lvds_priv->savePP_DIVISOR);*/
321 REG_WRITE(PP_CYCLE, lvds_priv->savePP_CYCLE);
322 REG_WRITE(PP_CONTROL, lvds_priv->savePP_CONTROL);
323 REG_WRITE(LVDS, lvds_priv->saveLVDS);
324
325 if (lvds_priv->savePP_CONTROL & POWER_TARGET_ON) {
326 REG_WRITE(PP_CONTROL, REG_READ(PP_CONTROL) |
327 POWER_TARGET_ON);
328 do {
329 pp_status = REG_READ(PP_STATUS);
330 } while ((pp_status & PP_ON) == 0);
331 } else {
332 REG_WRITE(PP_CONTROL, REG_READ(PP_CONTROL) &
333 ~POWER_TARGET_ON);
334 do {
335 pp_status = REG_READ(PP_STATUS);
336 } while (pp_status & PP_ON);
337 }
338}
339
340int psb_intel_lvds_mode_valid(struct drm_connector *connector,
341 struct drm_display_mode *mode)
342{
343 struct psb_intel_output *psb_intel_output =
344 to_psb_intel_output(connector);
345 struct drm_display_mode *fixed_mode =
346 psb_intel_output->mode_dev->panel_fixed_mode;
347
348 if (psb_intel_output->type == INTEL_OUTPUT_MIPI2)
349 fixed_mode = psb_intel_output->mode_dev->panel_fixed_mode2;
350
351 /* just in case */
352 if (mode->flags & DRM_MODE_FLAG_DBLSCAN)
353 return MODE_NO_DBLESCAN;
354
355 /* just in case */
356 if (mode->flags & DRM_MODE_FLAG_INTERLACE)
357 return MODE_NO_INTERLACE;
358
359 if (fixed_mode) {
360 if (mode->hdisplay > fixed_mode->hdisplay)
361 return MODE_PANEL;
362 if (mode->vdisplay > fixed_mode->vdisplay)
363 return MODE_PANEL;
364 }
365 return MODE_OK;
366}
367
368bool psb_intel_lvds_mode_fixup(struct drm_encoder *encoder,
369 struct drm_display_mode *mode,
370 struct drm_display_mode *adjusted_mode)
371{
372 struct psb_intel_mode_device *mode_dev =
373 enc_to_psb_intel_output(encoder)->mode_dev;
374 struct drm_device *dev = encoder->dev;
375 struct psb_intel_crtc *psb_intel_crtc =
376 to_psb_intel_crtc(encoder->crtc);
377 struct drm_encoder *tmp_encoder;
378 struct drm_display_mode *panel_fixed_mode = mode_dev->panel_fixed_mode;
379 struct psb_intel_output *psb_intel_output =
380 enc_to_psb_intel_output(encoder);
381
382 if (psb_intel_output->type == INTEL_OUTPUT_MIPI2)
383 panel_fixed_mode = mode_dev->panel_fixed_mode2;
384
385 /* FIXME: review for Medfield */
386 /* PSB requires the LVDS is on pipe B, MRST has only one pipe anyway */
387 if (!IS_MRST(dev) && psb_intel_crtc->pipe == 0) {
388 printk(KERN_ERR "Can't support LVDS on pipe A\n");
389 return false;
390 }
391 if (IS_MRST(dev) && psb_intel_crtc->pipe != 0) {
392 printk(KERN_ERR "Must use PIPE A\n");
393 return false;
394 }
395 /* Should never happen!! */
396 list_for_each_entry(tmp_encoder, &dev->mode_config.encoder_list,
397 head) {
398 if (tmp_encoder != encoder
399 && tmp_encoder->crtc == encoder->crtc) {
400 printk(KERN_ERR "Can't enable LVDS and another "
401 "encoder on the same pipe\n");
402 return false;
403 }
404 }
405
406 /*
407 * If we have timings from the BIOS for the panel, put them in
408 * to the adjusted mode. The CRTC will be set up for this mode,
409 * with the panel scaling set up to source from the H/VDisplay
410 * of the original mode.
411 */
412 if (panel_fixed_mode != NULL) {
413 adjusted_mode->hdisplay = panel_fixed_mode->hdisplay;
414 adjusted_mode->hsync_start = panel_fixed_mode->hsync_start;
415 adjusted_mode->hsync_end = panel_fixed_mode->hsync_end;
416 adjusted_mode->htotal = panel_fixed_mode->htotal;
417 adjusted_mode->vdisplay = panel_fixed_mode->vdisplay;
418 adjusted_mode->vsync_start = panel_fixed_mode->vsync_start;
419 adjusted_mode->vsync_end = panel_fixed_mode->vsync_end;
420 adjusted_mode->vtotal = panel_fixed_mode->vtotal;
421 adjusted_mode->clock = panel_fixed_mode->clock;
422 drm_mode_set_crtcinfo(adjusted_mode,
423 CRTC_INTERLACE_HALVE_V);
424 }
425
426 /*
427 * XXX: It would be nice to support lower refresh rates on the
428 * panels to reduce power consumption, and perhaps match the
429 * user's requested refresh rate.
430 */
431
432 return true;
433}
434
435static void psb_intel_lvds_prepare(struct drm_encoder *encoder)
436{
437 struct drm_device *dev = encoder->dev;
438 struct psb_intel_output *output = enc_to_psb_intel_output(encoder);
439 struct psb_intel_mode_device *mode_dev = output->mode_dev;
440
441 if (!gma_power_begin(dev, true))
442 return;
443
444 mode_dev->saveBLC_PWM_CTL = REG_READ(BLC_PWM_CTL);
445 mode_dev->backlight_duty_cycle = (mode_dev->saveBLC_PWM_CTL &
446 BACKLIGHT_DUTY_CYCLE_MASK);
447
448 psb_intel_lvds_set_power(dev, output, false);
449
450 gma_power_end(dev);
451}
452
453static void psb_intel_lvds_commit(struct drm_encoder *encoder)
454{
455 struct drm_device *dev = encoder->dev;
456 struct psb_intel_output *output = enc_to_psb_intel_output(encoder);
457 struct psb_intel_mode_device *mode_dev = output->mode_dev;
458
459 if (mode_dev->backlight_duty_cycle == 0)
460 mode_dev->backlight_duty_cycle =
461 psb_intel_lvds_get_max_backlight(dev);
462
463 psb_intel_lvds_set_power(dev, output, true);
464}
465
466static void psb_intel_lvds_mode_set(struct drm_encoder *encoder,
467 struct drm_display_mode *mode,
468 struct drm_display_mode *adjusted_mode)
469{
470 struct drm_device *dev = encoder->dev;
471 struct drm_psb_private *dev_priv = dev->dev_private;
472 u32 pfit_control;
473
474 /*
475 * The LVDS pin pair will already have been turned on in the
476 * psb_intel_crtc_mode_set since it has a large impact on the DPLL
477 * settings.
478 */
479
480 /*
481 * Enable automatic panel scaling so that non-native modes fill the
482 * screen. Should be enabled before the pipe is enabled, according to
483 * register description and PRM.
484 */
485 if (mode->hdisplay != adjusted_mode->hdisplay ||
486 mode->vdisplay != adjusted_mode->vdisplay)
487 pfit_control = (PFIT_ENABLE | VERT_AUTO_SCALE |
488 HORIZ_AUTO_SCALE | VERT_INTERP_BILINEAR |
489 HORIZ_INTERP_BILINEAR);
490 else
491 pfit_control = 0;
492
493 if (dev_priv->lvds_dither)
494 pfit_control |= PANEL_8TO6_DITHER_ENABLE;
495
496 REG_WRITE(PFIT_CONTROL, pfit_control);
497}
498
499/*
500 * Detect the LVDS connection.
501 *
502 * This always returns CONNECTOR_STATUS_CONNECTED.
503 * This connector should only have
504 * been set up if the LVDS was actually connected anyway.
505 */
506static enum drm_connector_status psb_intel_lvds_detect(struct drm_connector
507 *connector, bool force)
508{
509 return connector_status_connected;
510}
511
512/*
513 * Return the list of DDC modes if available, or the BIOS fixed mode otherwise.
514 */
515static int psb_intel_lvds_get_modes(struct drm_connector *connector)
516{
517 struct drm_device *dev = connector->dev;
518 struct psb_intel_output *psb_intel_output =
519 to_psb_intel_output(connector);
520 struct psb_intel_mode_device *mode_dev =
521 psb_intel_output->mode_dev;
522 int ret = 0;
523
524 if (!IS_MRST(dev))
525 ret = psb_intel_ddc_get_modes(psb_intel_output);
526
527 if (ret)
528 return ret;
529
530 /* Didn't get an EDID, so
531 * Set wide sync ranges so we get all modes
532 * handed to valid_mode for checking
533 */
534 connector->display_info.min_vfreq = 0;
535 connector->display_info.max_vfreq = 200;
536 connector->display_info.min_hfreq = 0;
537 connector->display_info.max_hfreq = 200;
538
539 if (mode_dev->panel_fixed_mode != NULL) {
540 struct drm_display_mode *mode =
541 drm_mode_duplicate(dev, mode_dev->panel_fixed_mode);
542 drm_mode_probed_add(connector, mode);
543 return 1;
544 }
545
546 return 0;
547}
548
549/**
550 * psb_intel_lvds_destroy - unregister and free LVDS structures
551 * @connector: connector to free
552 *
553 * Unregister the DDC bus for this connector then free the driver private
554 * structure.
555 */
556void psb_intel_lvds_destroy(struct drm_connector *connector)
557{
558 struct psb_intel_output *psb_intel_output =
559 to_psb_intel_output(connector);
560
561 if (psb_intel_output->ddc_bus)
562 psb_intel_i2c_destroy(psb_intel_output->ddc_bus);
563 drm_sysfs_connector_remove(connector);
564 drm_connector_cleanup(connector);
565 kfree(connector);
566}
567
568int psb_intel_lvds_set_property(struct drm_connector *connector,
569 struct drm_property *property,
570 uint64_t value)
571{
572 struct drm_encoder *encoder = connector->encoder;
573
574 if (!encoder)
575 return -1;
576
577 if (!strcmp(property->name, "scaling mode")) {
578 struct psb_intel_crtc *crtc =
579 to_psb_intel_crtc(encoder->crtc);
580 uint64_t curval;
581
582 if (!crtc)
583 goto set_prop_error;
584
585 switch (value) {
586 case DRM_MODE_SCALE_FULLSCREEN:
587 break;
588 case DRM_MODE_SCALE_NO_SCALE:
589 break;
590 case DRM_MODE_SCALE_ASPECT:
591 break;
592 default:
593 goto set_prop_error;
594 }
595
596 if (drm_connector_property_get_value(connector,
597 property,
598 &curval))
599 goto set_prop_error;
600
601 if (curval == value)
602 goto set_prop_done;
603
604 if (drm_connector_property_set_value(connector,
605 property,
606 value))
607 goto set_prop_error;
608
609 if (crtc->saved_mode.hdisplay != 0 &&
610 crtc->saved_mode.vdisplay != 0) {
611 if (!drm_crtc_helper_set_mode(encoder->crtc,
612 &crtc->saved_mode,
613 encoder->crtc->x,
614 encoder->crtc->y,
615 encoder->crtc->fb))
616 goto set_prop_error;
617 }
618 } else if (!strcmp(property->name, "backlight")) {
619 if (drm_connector_property_set_value(connector,
620 property,
621 value))
622 goto set_prop_error;
623 else {
624#ifdef CONFIG_BACKLIGHT_CLASS_DEVICE
625 struct drm_psb_private *devp = encoder->dev->dev_private;
626 struct backlight_device *bd = devp->backlight_device;
627 if (bd) {
628 bd->props.brightness = value;
629 backlight_update_status(bd);
630 }
631#endif
632 }
633 } else if (!strcmp(property->name, "DPMS")) {
634 struct drm_encoder_helper_funcs *hfuncs
635 = encoder->helper_private;
636 hfuncs->dpms(encoder, value);
637 }
638
639set_prop_done:
640 return 0;
641set_prop_error:
642 return -1;
643}
644
645static const struct drm_encoder_helper_funcs psb_intel_lvds_helper_funcs = {
646 .dpms = psb_intel_lvds_encoder_dpms,
647 .mode_fixup = psb_intel_lvds_mode_fixup,
648 .prepare = psb_intel_lvds_prepare,
649 .mode_set = psb_intel_lvds_mode_set,
650 .commit = psb_intel_lvds_commit,
651};
652
653const struct drm_connector_helper_funcs
654 psb_intel_lvds_connector_helper_funcs = {
655 .get_modes = psb_intel_lvds_get_modes,
656 .mode_valid = psb_intel_lvds_mode_valid,
657 .best_encoder = psb_intel_best_encoder,
658};
659
660const struct drm_connector_funcs psb_intel_lvds_connector_funcs = {
661 .dpms = drm_helper_connector_dpms,
662 .save = psb_intel_lvds_save,
663 .restore = psb_intel_lvds_restore,
664 .detect = psb_intel_lvds_detect,
665 .fill_modes = drm_helper_probe_single_connector_modes,
666 .set_property = psb_intel_lvds_set_property,
667 .destroy = psb_intel_lvds_destroy,
668};
669
670
671static void psb_intel_lvds_enc_destroy(struct drm_encoder *encoder)
672{
673 drm_encoder_cleanup(encoder);
674}
675
676const struct drm_encoder_funcs psb_intel_lvds_enc_funcs = {
677 .destroy = psb_intel_lvds_enc_destroy,
678};
679
680
681
682/**
683 * psb_intel_lvds_init - setup LVDS connectors on this device
684 * @dev: drm device
685 *
686 * Create the connector, register the LVDS DDC bus, and try to figure out what
687 * modes we can display on the LVDS panel (if present).
688 */
689void psb_intel_lvds_init(struct drm_device *dev,
690 struct psb_intel_mode_device *mode_dev)
691{
692 struct psb_intel_output *psb_intel_output;
693 struct psb_intel_lvds_priv *lvds_priv;
694 struct drm_connector *connector;
695 struct drm_encoder *encoder;
696 struct drm_display_mode *scan; /* *modes, *bios_mode; */
697 struct drm_crtc *crtc;
698 struct drm_psb_private *dev_priv =
699 (struct drm_psb_private *)dev->dev_private;
700 u32 lvds;
701 int pipe;
702
703 psb_intel_output = kzalloc(sizeof(struct psb_intel_output), GFP_KERNEL);
704 if (!psb_intel_output)
705 return;
706
707 lvds_priv = kzalloc(sizeof(struct psb_intel_lvds_priv), GFP_KERNEL);
708 if (!lvds_priv) {
709 kfree(psb_intel_output);
710 dev_err(dev->dev, "LVDS private allocation error\n");
711 return;
712 }
713
714 psb_intel_output->dev_priv = lvds_priv;
715
716 psb_intel_output->mode_dev = mode_dev;
717 connector = &psb_intel_output->base;
718 encoder = &psb_intel_output->enc;
719 drm_connector_init(dev, &psb_intel_output->base,
720 &psb_intel_lvds_connector_funcs,
721 DRM_MODE_CONNECTOR_LVDS);
722
723 drm_encoder_init(dev, &psb_intel_output->enc,
724 &psb_intel_lvds_enc_funcs,
725 DRM_MODE_ENCODER_LVDS);
726
727 drm_mode_connector_attach_encoder(&psb_intel_output->base,
728 &psb_intel_output->enc);
729 psb_intel_output->type = INTEL_OUTPUT_LVDS;
730
731 drm_encoder_helper_add(encoder, &psb_intel_lvds_helper_funcs);
732 drm_connector_helper_add(connector,
733 &psb_intel_lvds_connector_helper_funcs);
734 connector->display_info.subpixel_order = SubPixelHorizontalRGB;
735 connector->interlace_allowed = false;
736 connector->doublescan_allowed = false;
737
738 /*Attach connector properties*/
739 drm_connector_attach_property(connector,
740 dev->mode_config.scaling_mode_property,
741 DRM_MODE_SCALE_FULLSCREEN);
742 drm_connector_attach_property(connector,
743 dev_priv->backlight_property,
744 BRIGHTNESS_MAX_LEVEL);
745
746 /*
747 * Set up I2C bus
748 * FIXME: distroy i2c_bus when exit
749 */
750 psb_intel_output->i2c_bus = psb_intel_i2c_create(dev,
751 GPIOB,
752 "LVDSBLC_B");
753 if (!psb_intel_output->i2c_bus) {
754 dev_printk(KERN_ERR,
755 &dev->pdev->dev, "I2C bus registration failed.\n");
756 goto failed_blc_i2c;
757 }
758 psb_intel_output->i2c_bus->slave_addr = 0x2C;
759 dev_priv->lvds_i2c_bus = psb_intel_output->i2c_bus;
760
761 /*
762 * LVDS discovery:
763 * 1) check for EDID on DDC
764 * 2) check for VBT data
765 * 3) check to see if LVDS is already on
766 * if none of the above, no panel
767 * 4) make sure lid is open
768 * if closed, act like it's not there for now
769 */
770
771 /* Set up the DDC bus. */
772 psb_intel_output->ddc_bus = psb_intel_i2c_create(dev,
773 GPIOC,
774 "LVDSDDC_C");
775 if (!psb_intel_output->ddc_bus) {
776 dev_printk(KERN_ERR, &dev->pdev->dev,
777 "DDC bus registration " "failed.\n");
778 goto failed_ddc;
779 }
780
781 /*
782 * Attempt to get the fixed panel mode from DDC. Assume that the
783 * preferred mode is the right one.
784 */
785 psb_intel_ddc_get_modes(psb_intel_output);
786 list_for_each_entry(scan, &connector->probed_modes, head) {
787 if (scan->type & DRM_MODE_TYPE_PREFERRED) {
788 mode_dev->panel_fixed_mode =
789 drm_mode_duplicate(dev, scan);
790 goto out; /* FIXME: check for quirks */
791 }
792 }
793
794 /* Failed to get EDID, what about VBT? do we need this? */
795 if (mode_dev->vbt_mode)
796 mode_dev->panel_fixed_mode =
797 drm_mode_duplicate(dev, mode_dev->vbt_mode);
798
799 if (!mode_dev->panel_fixed_mode)
800 if (dev_priv->lfp_lvds_vbt_mode)
801 mode_dev->panel_fixed_mode =
802 drm_mode_duplicate(dev,
803 dev_priv->lfp_lvds_vbt_mode);
804
805 /*
806 * If we didn't get EDID, try checking if the panel is already turned
807 * on. If so, assume that whatever is currently programmed is the
808 * correct mode.
809 */
810 lvds = REG_READ(LVDS);
811 pipe = (lvds & LVDS_PIPEB_SELECT) ? 1 : 0;
812 crtc = psb_intel_get_crtc_from_pipe(dev, pipe);
813
814 if (crtc && (lvds & LVDS_PORT_EN)) {
815 mode_dev->panel_fixed_mode =
816 psb_intel_crtc_mode_get(dev, crtc);
817 if (mode_dev->panel_fixed_mode) {
818 mode_dev->panel_fixed_mode->type |=
819 DRM_MODE_TYPE_PREFERRED;
820 goto out; /* FIXME: check for quirks */
821 }
822 }
823
824 /* If we still don't have a mode after all that, give up. */
825 if (!mode_dev->panel_fixed_mode) {
826 dev_err(dev->dev, "Found no modes on the lvds, ignoring the LVDS\n");
827 goto failed_find;
828 }
829
830 /*
831 * Blacklist machines with BIOSes that list an LVDS panel without
832 * actually having one.
833 */
834out:
835 drm_sysfs_connector_add(connector);
836 return;
837
838failed_find:
839 if (psb_intel_output->ddc_bus)
840 psb_intel_i2c_destroy(psb_intel_output->ddc_bus);
841failed_ddc:
842 if (psb_intel_output->i2c_bus)
843 psb_intel_i2c_destroy(psb_intel_output->i2c_bus);
844failed_blc_i2c:
845 drm_encoder_cleanup(encoder);
846 drm_connector_cleanup(connector);
847 kfree(connector);
848}
849
diff --git a/drivers/gpu/drm/gma500/psb_intel_modes.c b/drivers/gpu/drm/gma500/psb_intel_modes.c
new file mode 100644
index 000000000000..bde1aff96190
--- /dev/null
+++ b/drivers/gpu/drm/gma500/psb_intel_modes.c
@@ -0,0 +1,77 @@
1/*
2 * Copyright (c) 2007 Intel Corporation
3 *
4 * This program is free software; you can redistribute it and/or modify it
5 * under the terms and conditions of the GNU General Public License,
6 * version 2, as published by the Free Software Foundation.
7 *
8 * This program is distributed in the hope it will be useful, but WITHOUT
9 * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
10 * FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for
11 * more details.
12 *
13 * You should have received a copy of the GNU General Public License along with
14 * this program; if not, write to the Free Software Foundation, Inc.,
15 * 51 Franklin St - Fifth Floor, Boston, MA 02110-1301 USA.
16 *
17 * Authers: Jesse Barnes <jesse.barnes@intel.com>
18 */
19
20#include <linux/i2c.h>
21#include <linux/fb.h>
22#include <drm/drmP.h>
23#include "psb_intel_drv.h"
24
25/**
26 * psb_intel_ddc_probe
27 *
28 */
29bool psb_intel_ddc_probe(struct psb_intel_output *psb_intel_output)
30{
31 u8 out_buf[] = { 0x0, 0x0 };
32 u8 buf[2];
33 int ret;
34 struct i2c_msg msgs[] = {
35 {
36 .addr = 0x50,
37 .flags = 0,
38 .len = 1,
39 .buf = out_buf,
40 },
41 {
42 .addr = 0x50,
43 .flags = I2C_M_RD,
44 .len = 1,
45 .buf = buf,
46 }
47 };
48
49 ret = i2c_transfer(&psb_intel_output->ddc_bus->adapter, msgs, 2);
50 if (ret == 2)
51 return true;
52
53 return false;
54}
55
56/**
57 * psb_intel_ddc_get_modes - get modelist from monitor
58 * @connector: DRM connector device to use
59 *
60 * Fetch the EDID information from @connector using the DDC bus.
61 */
62int psb_intel_ddc_get_modes(struct psb_intel_output *psb_intel_output)
63{
64 struct edid *edid;
65 int ret = 0;
66
67 edid =
68 drm_get_edid(&psb_intel_output->base,
69 &psb_intel_output->ddc_bus->adapter);
70 if (edid) {
71 drm_mode_connector_update_edid_property(&psb_intel_output->
72 base, edid);
73 ret = drm_add_edid_modes(&psb_intel_output->base, edid);
74 kfree(edid);
75 }
76 return ret;
77}
diff --git a/drivers/gpu/drm/gma500/psb_intel_reg.h b/drivers/gpu/drm/gma500/psb_intel_reg.h
new file mode 100644
index 000000000000..1ac16aa791c9
--- /dev/null
+++ b/drivers/gpu/drm/gma500/psb_intel_reg.h
@@ -0,0 +1,1235 @@
1/*
2 * Copyright (c) 2009, Intel Corporation.
3 *
4 * This program is free software; you can redistribute it and/or modify it
5 * under the terms and conditions of the GNU General Public License,
6 * version 2, as published by the Free Software Foundation.
7 *
8 * This program is distributed in the hope it will be useful, but WITHOUT
9 * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
10 * FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for
11 * more details.
12 *
13 * You should have received a copy of the GNU General Public License along with
14 * this program; if not, write to the Free Software Foundation, Inc.,
15 * 51 Franklin St - Fifth Floor, Boston, MA 02110-1301 USA.
16 */
17#ifndef __PSB_INTEL_REG_H__
18#define __PSB_INTEL_REG_H__
19
20#define BLC_PWM_CTL 0x61254
21#define BLC_PWM_CTL2 0x61250
22#define BLC_PWM_CTL_C 0x62254
23#define BLC_PWM_CTL2_C 0x62250
24#define BACKLIGHT_MODULATION_FREQ_SHIFT (17)
25/*
26 * This is the most significant 15 bits of the number of backlight cycles in a
27 * complete cycle of the modulated backlight control.
28 *
29 * The actual value is this field multiplied by two.
30 */
31#define BACKLIGHT_MODULATION_FREQ_MASK (0x7fff << 17)
32#define BLM_LEGACY_MODE (1 << 16)
33/*
34 * This is the number of cycles out of the backlight modulation cycle for which
35 * the backlight is on.
36 *
37 * This field must be no greater than the number of cycles in the complete
38 * backlight modulation cycle.
39 */
40#define BACKLIGHT_DUTY_CYCLE_SHIFT (0)
41#define BACKLIGHT_DUTY_CYCLE_MASK (0xffff)
42
43#define I915_GCFGC 0xf0
44#define I915_LOW_FREQUENCY_ENABLE (1 << 7)
45#define I915_DISPLAY_CLOCK_190_200_MHZ (0 << 4)
46#define I915_DISPLAY_CLOCK_333_MHZ (4 << 4)
47#define I915_DISPLAY_CLOCK_MASK (7 << 4)
48
49#define I855_HPLLCC 0xc0
50#define I855_CLOCK_CONTROL_MASK (3 << 0)
51#define I855_CLOCK_133_200 (0 << 0)
52#define I855_CLOCK_100_200 (1 << 0)
53#define I855_CLOCK_100_133 (2 << 0)
54#define I855_CLOCK_166_250 (3 << 0)
55
56/* I830 CRTC registers */
57#define HTOTAL_A 0x60000
58#define HBLANK_A 0x60004
59#define HSYNC_A 0x60008
60#define VTOTAL_A 0x6000c
61#define VBLANK_A 0x60010
62#define VSYNC_A 0x60014
63#define PIPEASRC 0x6001c
64#define BCLRPAT_A 0x60020
65#define VSYNCSHIFT_A 0x60028
66
67#define HTOTAL_B 0x61000
68#define HBLANK_B 0x61004
69#define HSYNC_B 0x61008
70#define VTOTAL_B 0x6100c
71#define VBLANK_B 0x61010
72#define VSYNC_B 0x61014
73#define PIPEBSRC 0x6101c
74#define BCLRPAT_B 0x61020
75#define VSYNCSHIFT_B 0x61028
76
77#define HTOTAL_C 0x62000
78#define HBLANK_C 0x62004
79#define HSYNC_C 0x62008
80#define VTOTAL_C 0x6200c
81#define VBLANK_C 0x62010
82#define VSYNC_C 0x62014
83#define PIPECSRC 0x6201c
84#define BCLRPAT_C 0x62020
85#define VSYNCSHIFT_C 0x62028
86
87#define PP_STATUS 0x61200
88# define PP_ON (1 << 31)
89/*
90 * Indicates that all dependencies of the panel are on:
91 *
92 * - PLL enabled
93 * - pipe enabled
94 * - LVDS/DVOB/DVOC on
95 */
96#define PP_READY (1 << 30)
97#define PP_SEQUENCE_NONE (0 << 28)
98#define PP_SEQUENCE_ON (1 << 28)
99#define PP_SEQUENCE_OFF (2 << 28)
100#define PP_SEQUENCE_MASK 0x30000000
101#define PP_CONTROL 0x61204
102#define POWER_TARGET_ON (1 << 0)
103
104#define LVDSPP_ON 0x61208
105#define LVDSPP_OFF 0x6120c
106#define PP_CYCLE 0x61210
107
108#define PFIT_CONTROL 0x61230
109#define PFIT_ENABLE (1 << 31)
110#define PFIT_PIPE_MASK (3 << 29)
111#define PFIT_PIPE_SHIFT 29
112#define PFIT_SCALING_MODE_PILLARBOX (1 << 27)
113#define PFIT_SCALING_MODE_LETTERBOX (3 << 26)
114#define VERT_INTERP_DISABLE (0 << 10)
115#define VERT_INTERP_BILINEAR (1 << 10)
116#define VERT_INTERP_MASK (3 << 10)
117#define VERT_AUTO_SCALE (1 << 9)
118#define HORIZ_INTERP_DISABLE (0 << 6)
119#define HORIZ_INTERP_BILINEAR (1 << 6)
120#define HORIZ_INTERP_MASK (3 << 6)
121#define HORIZ_AUTO_SCALE (1 << 5)
122#define PANEL_8TO6_DITHER_ENABLE (1 << 3)
123
124#define PFIT_PGM_RATIOS 0x61234
125#define PFIT_VERT_SCALE_MASK 0xfff00000
126#define PFIT_HORIZ_SCALE_MASK 0x0000fff0
127
128#define PFIT_AUTO_RATIOS 0x61238
129
130#define DPLL_A 0x06014
131#define DPLL_B 0x06018
132#define DPLL_VCO_ENABLE (1 << 31)
133#define DPLL_DVO_HIGH_SPEED (1 << 30)
134#define DPLL_SYNCLOCK_ENABLE (1 << 29)
135#define DPLL_VGA_MODE_DIS (1 << 28)
136#define DPLLB_MODE_DAC_SERIAL (1 << 26) /* i915 */
137#define DPLLB_MODE_LVDS (2 << 26) /* i915 */
138#define DPLL_MODE_MASK (3 << 26)
139#define DPLL_DAC_SERIAL_P2_CLOCK_DIV_10 (0 << 24) /* i915 */
140#define DPLL_DAC_SERIAL_P2_CLOCK_DIV_5 (1 << 24) /* i915 */
141#define DPLLB_LVDS_P2_CLOCK_DIV_14 (0 << 24) /* i915 */
142#define DPLLB_LVDS_P2_CLOCK_DIV_7 (1 << 24) /* i915 */
143#define DPLL_P2_CLOCK_DIV_MASK 0x03000000 /* i915 */
144#define DPLL_FPA01_P1_POST_DIV_MASK 0x00ff0000 /* i915 */
145#define DPLL_LOCK (1 << 15) /* CDV */
146
147/*
148 * The i830 generation, in DAC/serial mode, defines p1 as two plus this
149 * bitfield, or just 2 if PLL_P1_DIVIDE_BY_TWO is set.
150 */
151# define DPLL_FPA01_P1_POST_DIV_MASK_I830 0x001f0000
152/*
153 * The i830 generation, in LVDS mode, defines P1 as the bit number set within
154 * this field (only one bit may be set).
155 */
156#define DPLL_FPA01_P1_POST_DIV_MASK_I830_LVDS 0x003f0000
157#define DPLL_FPA01_P1_POST_DIV_SHIFT 16
158#define PLL_P2_DIVIDE_BY_4 (1 << 23) /* i830, required
159 * in DVO non-gang */
160# define PLL_P1_DIVIDE_BY_TWO (1 << 21) /* i830 */
161#define PLL_REF_INPUT_DREFCLK (0 << 13)
162#define PLL_REF_INPUT_TVCLKINA (1 << 13) /* i830 */
163#define PLL_REF_INPUT_TVCLKINBC (2 << 13) /* SDVO
164 * TVCLKIN */
165#define PLLB_REF_INPUT_SPREADSPECTRUMIN (3 << 13)
166#define PLL_REF_INPUT_MASK (3 << 13)
167#define PLL_LOAD_PULSE_PHASE_SHIFT 9
168/*
169 * Parallel to Serial Load Pulse phase selection.
170 * Selects the phase for the 10X DPLL clock for the PCIe
171 * digital display port. The range is 4 to 13; 10 or more
172 * is just a flip delay. The default is 6
173 */
174#define PLL_LOAD_PULSE_PHASE_MASK (0xf << PLL_LOAD_PULSE_PHASE_SHIFT)
175#define DISPLAY_RATE_SELECT_FPA1 (1 << 8)
176
177/*
178 * SDVO multiplier for 945G/GM. Not used on 965.
179 *
180 * DPLL_MD_UDI_MULTIPLIER_MASK
181 */
182#define SDVO_MULTIPLIER_MASK 0x000000ff
183#define SDVO_MULTIPLIER_SHIFT_HIRES 4
184#define SDVO_MULTIPLIER_SHIFT_VGA 0
185
186/*
187 * PLL_MD
188 */
189/* Pipe A SDVO/UDI clock multiplier/divider register for G965. */
190#define DPLL_A_MD 0x0601c
191/* Pipe B SDVO/UDI clock multiplier/divider register for G965. */
192#define DPLL_B_MD 0x06020
193/*
194 * UDI pixel divider, controlling how many pixels are stuffed into a packet.
195 *
196 * Value is pixels minus 1. Must be set to 1 pixel for SDVO.
197 */
198#define DPLL_MD_UDI_DIVIDER_MASK 0x3f000000
199#define DPLL_MD_UDI_DIVIDER_SHIFT 24
200/* UDI pixel divider for VGA, same as DPLL_MD_UDI_DIVIDER_MASK. */
201#define DPLL_MD_VGA_UDI_DIVIDER_MASK 0x003f0000
202#define DPLL_MD_VGA_UDI_DIVIDER_SHIFT 16
203/*
204 * SDVO/UDI pixel multiplier.
205 *
206 * SDVO requires that the bus clock rate be between 1 and 2 Ghz, and the bus
207 * clock rate is 10 times the DPLL clock. At low resolution/refresh rate
208 * modes, the bus rate would be below the limits, so SDVO allows for stuffing
209 * dummy bytes in the datastream at an increased clock rate, with both sides of
210 * the link knowing how many bytes are fill.
211 *
212 * So, for a mode with a dotclock of 65Mhz, we would want to double the clock
213 * rate to 130Mhz to get a bus rate of 1.30Ghz. The DPLL clock rate would be
214 * set to 130Mhz, and the SDVO multiplier set to 2x in this register and
215 * through an SDVO command.
216 *
217 * This register field has values of multiplication factor minus 1, with
218 * a maximum multiplier of 5 for SDVO.
219 */
220#define DPLL_MD_UDI_MULTIPLIER_MASK 0x00003f00
221#define DPLL_MD_UDI_MULTIPLIER_SHIFT 8
222/*
223 * SDVO/UDI pixel multiplier for VGA, same as DPLL_MD_UDI_MULTIPLIER_MASK.
224 * This best be set to the default value (3) or the CRT won't work. No,
225 * I don't entirely understand what this does...
226 */
227#define DPLL_MD_VGA_UDI_MULTIPLIER_MASK 0x0000003f
228#define DPLL_MD_VGA_UDI_MULTIPLIER_SHIFT 0
229
230#define DPLL_TEST 0x606c
231#define DPLLB_TEST_SDVO_DIV_1 (0 << 22)
232#define DPLLB_TEST_SDVO_DIV_2 (1 << 22)
233#define DPLLB_TEST_SDVO_DIV_4 (2 << 22)
234#define DPLLB_TEST_SDVO_DIV_MASK (3 << 22)
235#define DPLLB_TEST_N_BYPASS (1 << 19)
236#define DPLLB_TEST_M_BYPASS (1 << 18)
237#define DPLLB_INPUT_BUFFER_ENABLE (1 << 16)
238#define DPLLA_TEST_N_BYPASS (1 << 3)
239#define DPLLA_TEST_M_BYPASS (1 << 2)
240#define DPLLA_INPUT_BUFFER_ENABLE (1 << 0)
241
242#define ADPA 0x61100
243#define ADPA_DAC_ENABLE (1 << 31)
244#define ADPA_DAC_DISABLE 0
245#define ADPA_PIPE_SELECT_MASK (1 << 30)
246#define ADPA_PIPE_A_SELECT 0
247#define ADPA_PIPE_B_SELECT (1 << 30)
248#define ADPA_USE_VGA_HVPOLARITY (1 << 15)
249#define ADPA_SETS_HVPOLARITY 0
250#define ADPA_VSYNC_CNTL_DISABLE (1 << 11)
251#define ADPA_VSYNC_CNTL_ENABLE 0
252#define ADPA_HSYNC_CNTL_DISABLE (1 << 10)
253#define ADPA_HSYNC_CNTL_ENABLE 0
254#define ADPA_VSYNC_ACTIVE_HIGH (1 << 4)
255#define ADPA_VSYNC_ACTIVE_LOW 0
256#define ADPA_HSYNC_ACTIVE_HIGH (1 << 3)
257#define ADPA_HSYNC_ACTIVE_LOW 0
258
259#define FPA0 0x06040
260#define FPA1 0x06044
261#define FPB0 0x06048
262#define FPB1 0x0604c
263#define FP_N_DIV_MASK 0x003f0000
264#define FP_N_DIV_SHIFT 16
265#define FP_M1_DIV_MASK 0x00003f00
266#define FP_M1_DIV_SHIFT 8
267#define FP_M2_DIV_MASK 0x0000003f
268#define FP_M2_DIV_SHIFT 0
269
270#define PORT_HOTPLUG_EN 0x61110
271#define SDVOB_HOTPLUG_INT_EN (1 << 26)
272#define SDVOC_HOTPLUG_INT_EN (1 << 25)
273#define TV_HOTPLUG_INT_EN (1 << 18)
274#define CRT_HOTPLUG_INT_EN (1 << 9)
275#define CRT_HOTPLUG_FORCE_DETECT (1 << 3)
276/* CDV.. */
277#define CRT_HOTPLUG_ACTIVATION_PERIOD_64 (1 << 8)
278#define CRT_HOTPLUG_DAC_ON_TIME_2M (0 << 7)
279#define CRT_HOTPLUG_DAC_ON_TIME_4M (1 << 7)
280#define CRT_HOTPLUG_VOLTAGE_COMPARE_40 (0 << 5)
281#define CRT_HOTPLUG_VOLTAGE_COMPARE_50 (1 << 5)
282#define CRT_HOTPLUG_VOLTAGE_COMPARE_60 (2 << 5)
283#define CRT_HOTPLUG_VOLTAGE_COMPARE_70 (3 << 5)
284#define CRT_HOTPLUG_VOLTAGE_COMPARE_MASK (3 << 5)
285#define CRT_HOTPLUG_DETECT_DELAY_1G (0 << 4)
286#define CRT_HOTPLUG_DETECT_DELAY_2G (1 << 4)
287#define CRT_HOTPLUG_DETECT_VOLTAGE_325MV (0 << 2)
288#define CRT_HOTPLUG_DETECT_VOLTAGE_475MV (1 << 2)
289#define CRT_HOTPLUG_DETECT_MASK 0x000000F8
290
291#define PORT_HOTPLUG_STAT 0x61114
292#define CRT_HOTPLUG_INT_STATUS (1 << 11)
293#define TV_HOTPLUG_INT_STATUS (1 << 10)
294#define CRT_HOTPLUG_MONITOR_MASK (3 << 8)
295#define CRT_HOTPLUG_MONITOR_COLOR (3 << 8)
296#define CRT_HOTPLUG_MONITOR_MONO (2 << 8)
297#define CRT_HOTPLUG_MONITOR_NONE (0 << 8)
298#define SDVOC_HOTPLUG_INT_STATUS (1 << 7)
299#define SDVOB_HOTPLUG_INT_STATUS (1 << 6)
300
301#define SDVOB 0x61140
302#define SDVOC 0x61160
303#define SDVO_ENABLE (1 << 31)
304#define SDVO_PIPE_B_SELECT (1 << 30)
305#define SDVO_STALL_SELECT (1 << 29)
306#define SDVO_INTERRUPT_ENABLE (1 << 26)
307
308/**
309 * 915G/GM SDVO pixel multiplier.
310 *
311 * Programmed value is multiplier - 1, up to 5x.
312 *
313 * DPLL_MD_UDI_MULTIPLIER_MASK
314 */
315#define SDVO_PORT_MULTIPLY_MASK (7 << 23)
316#define SDVO_PORT_MULTIPLY_SHIFT 23
317#define SDVO_PHASE_SELECT_MASK (15 << 19)
318#define SDVO_PHASE_SELECT_DEFAULT (6 << 19)
319#define SDVO_CLOCK_OUTPUT_INVERT (1 << 18)
320#define SDVOC_GANG_MODE (1 << 16)
321#define SDVO_BORDER_ENABLE (1 << 7)
322#define SDVOB_PCIE_CONCURRENCY (1 << 3)
323#define SDVO_DETECTED (1 << 2)
324/* Bits to be preserved when writing */
325#define SDVOB_PRESERVE_MASK ((1 << 17) | (1 << 16) | (1 << 14))
326#define SDVOC_PRESERVE_MASK (1 << 17)
327
328/*
329 * This register controls the LVDS output enable, pipe selection, and data
330 * format selection.
331 *
332 * All of the clock/data pairs are force powered down by power sequencing.
333 */
334#define LVDS 0x61180
335/*
336 * Enables the LVDS port. This bit must be set before DPLLs are enabled, as
337 * the DPLL semantics change when the LVDS is assigned to that pipe.
338 */
339#define LVDS_PORT_EN (1 << 31)
340/* Selects pipe B for LVDS data. Must be set on pre-965. */
341#define LVDS_PIPEB_SELECT (1 << 30)
342
343/* Turns on border drawing to allow centered display. */
344#define LVDS_BORDER_EN (1 << 15)
345
346/*
347 * Enables the A0-A2 data pairs and CLKA, containing 18 bits of color data per
348 * pixel.
349 */
350#define LVDS_A0A2_CLKA_POWER_MASK (3 << 8)
351#define LVDS_A0A2_CLKA_POWER_DOWN (0 << 8)
352#define LVDS_A0A2_CLKA_POWER_UP (3 << 8)
353/*
354 * Controls the A3 data pair, which contains the additional LSBs for 24 bit
355 * mode. Only enabled if LVDS_A0A2_CLKA_POWER_UP also indicates it should be
356 * on.
357 */
358#define LVDS_A3_POWER_MASK (3 << 6)
359#define LVDS_A3_POWER_DOWN (0 << 6)
360#define LVDS_A3_POWER_UP (3 << 6)
361/*
362 * Controls the CLKB pair. This should only be set when LVDS_B0B3_POWER_UP
363 * is set.
364 */
365#define LVDS_CLKB_POWER_MASK (3 << 4)
366#define LVDS_CLKB_POWER_DOWN (0 << 4)
367#define LVDS_CLKB_POWER_UP (3 << 4)
368/*
369 * Controls the B0-B3 data pairs. This must be set to match the DPLL p2
370 * setting for whether we are in dual-channel mode. The B3 pair will
371 * additionally only be powered up when LVDS_A3_POWER_UP is set.
372 */
373#define LVDS_B0B3_POWER_MASK (3 << 2)
374#define LVDS_B0B3_POWER_DOWN (0 << 2)
375#define LVDS_B0B3_POWER_UP (3 << 2)
376
377#define PIPEACONF 0x70008
378#define PIPEACONF_ENABLE (1 << 31)
379#define PIPEACONF_DISABLE 0
380#define PIPEACONF_DOUBLE_WIDE (1 << 30)
381#define PIPECONF_ACTIVE (1 << 30)
382#define I965_PIPECONF_ACTIVE (1 << 30)
383#define PIPECONF_DSIPLL_LOCK (1 << 29)
384#define PIPEACONF_SINGLE_WIDE 0
385#define PIPEACONF_PIPE_UNLOCKED 0
386#define PIPEACONF_DSR (1 << 26)
387#define PIPEACONF_PIPE_LOCKED (1 << 25)
388#define PIPEACONF_PALETTE 0
389#define PIPECONF_FORCE_BORDER (1 << 25)
390#define PIPEACONF_GAMMA (1 << 24)
391#define PIPECONF_PROGRESSIVE (0 << 21)
392#define PIPECONF_INTERLACE_W_FIELD_INDICATION (6 << 21)
393#define PIPECONF_INTERLACE_FIELD_0_ONLY (7 << 21)
394#define PIPECONF_PLANE_OFF (1 << 19)
395#define PIPECONF_CURSOR_OFF (1 << 18)
396
397#define PIPEBCONF 0x71008
398#define PIPEBCONF_ENABLE (1 << 31)
399#define PIPEBCONF_DISABLE 0
400#define PIPEBCONF_DOUBLE_WIDE (1 << 30)
401#define PIPEBCONF_DISABLE 0
402#define PIPEBCONF_GAMMA (1 << 24)
403#define PIPEBCONF_PALETTE 0
404
405#define PIPECCONF 0x72008
406
407#define PIPEBGCMAXRED 0x71010
408#define PIPEBGCMAXGREEN 0x71014
409#define PIPEBGCMAXBLUE 0x71018
410
411#define PIPEASTAT 0x70024
412#define PIPEBSTAT 0x71024
413#define PIPECSTAT 0x72024
414#define PIPE_VBLANK_INTERRUPT_STATUS (1UL << 1)
415#define PIPE_START_VBLANK_INTERRUPT_STATUS (1UL << 2)
416#define PIPE_VBLANK_CLEAR (1 << 1)
417#define PIPE_VBLANK_STATUS (1 << 1)
418#define PIPE_TE_STATUS (1UL << 6)
419#define PIPE_DPST_EVENT_STATUS (1UL << 7)
420#define PIPE_VSYNC_CLEAR (1UL << 9)
421#define PIPE_VSYNC_STATUS (1UL << 9)
422#define PIPE_HDMI_AUDIO_UNDERRUN_STATUS (1UL << 10)
423#define PIPE_HDMI_AUDIO_BUFFER_DONE_STATUS (1UL << 11)
424#define PIPE_VBLANK_INTERRUPT_ENABLE (1UL << 17)
425#define PIPE_START_VBLANK_INTERRUPT_ENABLE (1UL << 18)
426#define PIPE_TE_ENABLE (1UL << 22)
427#define PIPE_DPST_EVENT_ENABLE (1UL << 23)
428#define PIPE_VSYNC_ENABL (1UL << 25)
429#define PIPE_HDMI_AUDIO_UNDERRUN (1UL << 26)
430#define PIPE_HDMI_AUDIO_BUFFER_DONE (1UL << 27)
431#define PIPE_HDMI_AUDIO_INT_MASK (PIPE_HDMI_AUDIO_UNDERRUN | \
432 PIPE_HDMI_AUDIO_BUFFER_DONE)
433#define PIPE_EVENT_MASK ((1 << 29)|(1 << 28)|(1 << 27)|(1 << 26)|(1 << 24)|(1 << 23)|(1 << 22)|(1 << 21)|(1 << 20)|(1 << 16))
434#define PIPE_VBLANK_MASK ((1 << 25)|(1 << 24)|(1 << 18)|(1 << 17))
435#define HISTOGRAM_INT_CONTROL 0x61268
436#define HISTOGRAM_BIN_DATA 0X61264
437#define HISTOGRAM_LOGIC_CONTROL 0x61260
438#define PWM_CONTROL_LOGIC 0x61250
439#define PIPE_HOTPLUG_INTERRUPT_STATUS (1UL << 10)
440#define HISTOGRAM_INTERRUPT_ENABLE (1UL << 31)
441#define HISTOGRAM_LOGIC_ENABLE (1UL << 31)
442#define PWM_LOGIC_ENABLE (1UL << 31)
443#define PWM_PHASEIN_ENABLE (1UL << 25)
444#define PWM_PHASEIN_INT_ENABLE (1UL << 24)
445#define PWM_PHASEIN_VB_COUNT 0x00001f00
446#define PWM_PHASEIN_INC 0x0000001f
447#define HISTOGRAM_INT_CTRL_CLEAR (1UL << 30)
448#define DPST_YUV_LUMA_MODE 0
449
450struct dpst_ie_histogram_control {
451 union {
452 uint32_t data;
453 struct {
454 uint32_t bin_reg_index:7;
455 uint32_t reserved:4;
456 uint32_t bin_reg_func_select:1;
457 uint32_t sync_to_phase_in:1;
458 uint32_t alt_enhancement_mode:2;
459 uint32_t reserved1:1;
460 uint32_t sync_to_phase_in_count:8;
461 uint32_t histogram_mode_select:1;
462 uint32_t reserved2:4;
463 uint32_t ie_pipe_assignment:1;
464 uint32_t ie_mode_table_enabled:1;
465 uint32_t ie_histogram_enable:1;
466 };
467 };
468};
469
470struct dpst_guardband {
471 union {
472 uint32_t data;
473 struct {
474 uint32_t guardband:22;
475 uint32_t guardband_interrupt_delay:8;
476 uint32_t interrupt_status:1;
477 uint32_t interrupt_enable:1;
478 };
479 };
480};
481
482#define PIPEAFRAMEHIGH 0x70040
483#define PIPEAFRAMEPIXEL 0x70044
484#define PIPEBFRAMEHIGH 0x71040
485#define PIPEBFRAMEPIXEL 0x71044
486#define PIPECFRAMEHIGH 0x72040
487#define PIPECFRAMEPIXEL 0x72044
488#define PIPE_FRAME_HIGH_MASK 0x0000ffff
489#define PIPE_FRAME_HIGH_SHIFT 0
490#define PIPE_FRAME_LOW_MASK 0xff000000
491#define PIPE_FRAME_LOW_SHIFT 24
492#define PIPE_PIXEL_MASK 0x00ffffff
493#define PIPE_PIXEL_SHIFT 0
494
495#define DSPARB 0x70030
496#define DSPFW1 0x70034
497#define DSPFW2 0x70038
498#define DSPFW3 0x7003c
499#define DSPFW4 0x70050
500#define DSPFW5 0x70054
501#define DSPFW6 0x70058
502#define DSPCHICKENBIT 0x70400
503#define DSPACNTR 0x70180
504#define DSPBCNTR 0x71180
505#define DSPCCNTR 0x72180
506#define DISPLAY_PLANE_ENABLE (1 << 31)
507#define DISPLAY_PLANE_DISABLE 0
508#define DISPPLANE_GAMMA_ENABLE (1 << 30)
509#define DISPPLANE_GAMMA_DISABLE 0
510#define DISPPLANE_PIXFORMAT_MASK (0xf << 26)
511#define DISPPLANE_8BPP (0x2 << 26)
512#define DISPPLANE_15_16BPP (0x4 << 26)
513#define DISPPLANE_16BPP (0x5 << 26)
514#define DISPPLANE_32BPP_NO_ALPHA (0x6 << 26)
515#define DISPPLANE_32BPP (0x7 << 26)
516#define DISPPLANE_STEREO_ENABLE (1 << 25)
517#define DISPPLANE_STEREO_DISABLE 0
518#define DISPPLANE_SEL_PIPE_MASK (1 << 24)
519#define DISPPLANE_SEL_PIPE_POS 24
520#define DISPPLANE_SEL_PIPE_A 0
521#define DISPPLANE_SEL_PIPE_B (1 << 24)
522#define DISPPLANE_SRC_KEY_ENABLE (1 << 22)
523#define DISPPLANE_SRC_KEY_DISABLE 0
524#define DISPPLANE_LINE_DOUBLE (1 << 20)
525#define DISPPLANE_NO_LINE_DOUBLE 0
526#define DISPPLANE_STEREO_POLARITY_FIRST 0
527#define DISPPLANE_STEREO_POLARITY_SECOND (1 << 18)
528/* plane B only */
529#define DISPPLANE_ALPHA_TRANS_ENABLE (1 << 15)
530#define DISPPLANE_ALPHA_TRANS_DISABLE 0
531#define DISPPLANE_SPRITE_ABOVE_DISPLAYA 0
532#define DISPPLANE_SPRITE_ABOVE_OVERLAY (1)
533#define DISPPLANE_BOTTOM (4)
534
535#define DSPABASE 0x70184
536#define DSPALINOFF 0x70184
537#define DSPASTRIDE 0x70188
538
539#define DSPBBASE 0x71184
540#define DSPBLINOFF 0X71184
541#define DSPBADDR DSPBBASE
542#define DSPBSTRIDE 0x71188
543
544#define DSPCBASE 0x72184
545#define DSPCLINOFF 0x72184
546#define DSPCSTRIDE 0x72188
547
548#define DSPAKEYVAL 0x70194
549#define DSPAKEYMASK 0x70198
550
551#define DSPAPOS 0x7018C /* reserved */
552#define DSPASIZE 0x70190
553#define DSPBPOS 0x7118C
554#define DSPBSIZE 0x71190
555#define DSPCPOS 0x7218C
556#define DSPCSIZE 0x72190
557
558#define DSPASURF 0x7019C
559#define DSPATILEOFF 0x701A4
560
561#define DSPBSURF 0x7119C
562#define DSPBTILEOFF 0x711A4
563
564#define DSPCSURF 0x7219C
565#define DSPCTILEOFF 0x721A4
566#define DSPCKEYMAXVAL 0x721A0
567#define DSPCKEYMINVAL 0x72194
568#define DSPCKEYMSK 0x72198
569
570#define VGACNTRL 0x71400
571#define VGA_DISP_DISABLE (1 << 31)
572#define VGA_2X_MODE (1 << 30)
573#define VGA_PIPE_B_SELECT (1 << 29)
574
575/*
576 * Overlay registers
577 */
578#define OV_C_OFFSET 0x08000
579#define OV_OVADD 0x30000
580#define OV_DOVASTA 0x30008
581# define OV_PIPE_SELECT ((1 << 6)|(1 << 7))
582# define OV_PIPE_SELECT_POS 6
583# define OV_PIPE_A 0
584# define OV_PIPE_C 1
585#define OV_OGAMC5 0x30010
586#define OV_OGAMC4 0x30014
587#define OV_OGAMC3 0x30018
588#define OV_OGAMC2 0x3001C
589#define OV_OGAMC1 0x30020
590#define OV_OGAMC0 0x30024
591#define OVC_OVADD 0x38000
592#define OVC_DOVCSTA 0x38008
593#define OVC_OGAMC5 0x38010
594#define OVC_OGAMC4 0x38014
595#define OVC_OGAMC3 0x38018
596#define OVC_OGAMC2 0x3801C
597#define OVC_OGAMC1 0x38020
598#define OVC_OGAMC0 0x38024
599
600/*
601 * Some BIOS scratch area registers. The 845 (and 830?) store the amount
602 * of video memory available to the BIOS in SWF1.
603 */
604#define SWF0 0x71410
605#define SWF1 0x71414
606#define SWF2 0x71418
607#define SWF3 0x7141c
608#define SWF4 0x71420
609#define SWF5 0x71424
610#define SWF6 0x71428
611
612/*
613 * 855 scratch registers.
614 */
615#define SWF00 0x70410
616#define SWF01 0x70414
617#define SWF02 0x70418
618#define SWF03 0x7041c
619#define SWF04 0x70420
620#define SWF05 0x70424
621#define SWF06 0x70428
622
623#define SWF10 SWF0
624#define SWF11 SWF1
625#define SWF12 SWF2
626#define SWF13 SWF3
627#define SWF14 SWF4
628#define SWF15 SWF5
629#define SWF16 SWF6
630
631#define SWF30 0x72414
632#define SWF31 0x72418
633#define SWF32 0x7241c
634
635
636/*
637 * Palette registers
638 */
639#define PALETTE_A 0x0a000
640#define PALETTE_B 0x0a800
641#define PALETTE_C 0x0ac00
642
643/* Cursor A & B regs */
644#define CURACNTR 0x70080
645#define CURSOR_MODE_DISABLE 0x00
646#define CURSOR_MODE_64_32B_AX 0x07
647#define CURSOR_MODE_64_ARGB_AX ((1 << 5) | CURSOR_MODE_64_32B_AX)
648#define MCURSOR_GAMMA_ENABLE (1 << 26)
649#define CURABASE 0x70084
650#define CURAPOS 0x70088
651#define CURSOR_POS_MASK 0x007FF
652#define CURSOR_POS_SIGN 0x8000
653#define CURSOR_X_SHIFT 0
654#define CURSOR_Y_SHIFT 16
655#define CURBCNTR 0x700c0
656#define CURBBASE 0x700c4
657#define CURBPOS 0x700c8
658#define CURCCNTR 0x700e0
659#define CURCBASE 0x700e4
660#define CURCPOS 0x700e8
661
662/*
663 * Interrupt Registers
664 */
665#define IER 0x020a0
666#define IIR 0x020a4
667#define IMR 0x020a8
668#define ISR 0x020ac
669
670/*
671 * MOORESTOWN delta registers
672 */
673#define MRST_DPLL_A 0x0f014
674#define MDFLD_DPLL_B 0x0f018
675#define MDFLD_INPUT_REF_SEL (1 << 14)
676#define MDFLD_VCO_SEL (1 << 16)
677#define DPLLA_MODE_LVDS (2 << 26) /* mrst */
678#define MDFLD_PLL_LATCHEN (1 << 28)
679#define MDFLD_PWR_GATE_EN (1 << 30)
680#define MDFLD_P1_MASK (0x1FF << 17)
681#define MRST_FPA0 0x0f040
682#define MRST_FPA1 0x0f044
683#define MDFLD_DPLL_DIV0 0x0f048
684#define MDFLD_DPLL_DIV1 0x0f04c
685#define MRST_PERF_MODE 0x020f4
686
687/*
688 * MEDFIELD HDMI registers
689 */
690#define HDMIPHYMISCCTL 0x61134
691#define HDMI_PHY_POWER_DOWN 0x7f
692#define HDMIB_CONTROL 0x61140
693#define HDMIB_PORT_EN (1 << 31)
694#define HDMIB_PIPE_B_SELECT (1 << 30)
695#define HDMIB_NULL_PACKET (1 << 9)
696#define HDMIB_HDCP_PORT (1 << 5)
697
698/* #define LVDS 0x61180 */
699#define MRST_PANEL_8TO6_DITHER_ENABLE (1 << 25)
700#define MRST_PANEL_24_DOT_1_FORMAT (1 << 24)
701#define LVDS_A3_POWER_UP_0_OUTPUT (1 << 6)
702
703#define MIPI 0x61190
704#define MIPI_C 0x62190
705#define MIPI_PORT_EN (1 << 31)
706/* Turns on border drawing to allow centered display. */
707#define SEL_FLOPPED_HSTX (1 << 23)
708#define PASS_FROM_SPHY_TO_AFE (1 << 16)
709#define MIPI_BORDER_EN (1 << 15)
710#define MIPIA_3LANE_MIPIC_1LANE 0x1
711#define MIPIA_2LANE_MIPIC_2LANE 0x2
712#define TE_TRIGGER_DSI_PROTOCOL (1 << 2)
713#define TE_TRIGGER_GPIO_PIN (1 << 3)
714#define MIPI_TE_COUNT 0x61194
715
716/* #define PP_CONTROL 0x61204 */
717#define POWER_DOWN_ON_RESET (1 << 1)
718
719/* #define PFIT_CONTROL 0x61230 */
720#define PFIT_PIPE_SELECT (3 << 29)
721#define PFIT_PIPE_SELECT_SHIFT (29)
722
723/* #define BLC_PWM_CTL 0x61254 */
724#define MRST_BACKLIGHT_MODULATION_FREQ_SHIFT (16)
725#define MRST_BACKLIGHT_MODULATION_FREQ_MASK (0xffff << 16)
726
727/* #define PIPEACONF 0x70008 */
728#define PIPEACONF_PIPE_STATE (1 << 30)
729/* #define DSPACNTR 0x70180 */
730
731#define MRST_DSPABASE 0x7019c
732#define MRST_DSPBBASE 0x7119c
733#define MDFLD_DSPCBASE 0x7219c
734
735/*
736 * Moorestown registers.
737 */
738
739/*
740 * MIPI IP registers
741 */
742#define MIPIC_REG_OFFSET 0x800
743
744#define DEVICE_READY_REG 0xb000
745#define LP_OUTPUT_HOLD (1 << 16)
746#define EXIT_ULPS_DEV_READY 0x3
747#define LP_OUTPUT_HOLD_RELEASE 0x810000
748# define ENTERING_ULPS (2 << 1)
749# define EXITING_ULPS (1 << 1)
750# define ULPS_MASK (3 << 1)
751# define BUS_POSSESSION (1 << 3)
752#define INTR_STAT_REG 0xb004
753#define RX_SOT_ERROR (1 << 0)
754#define RX_SOT_SYNC_ERROR (1 << 1)
755#define RX_ESCAPE_MODE_ENTRY_ERROR (1 << 3)
756#define RX_LP_TX_SYNC_ERROR (1 << 4)
757#define RX_HS_RECEIVE_TIMEOUT_ERROR (1 << 5)
758#define RX_FALSE_CONTROL_ERROR (1 << 6)
759#define RX_ECC_SINGLE_BIT_ERROR (1 << 7)
760#define RX_ECC_MULTI_BIT_ERROR (1 << 8)
761#define RX_CHECKSUM_ERROR (1 << 9)
762#define RX_DSI_DATA_TYPE_NOT_RECOGNIZED (1 << 10)
763#define RX_DSI_VC_ID_INVALID (1 << 11)
764#define TX_FALSE_CONTROL_ERROR (1 << 12)
765#define TX_ECC_SINGLE_BIT_ERROR (1 << 13)
766#define TX_ECC_MULTI_BIT_ERROR (1 << 14)
767#define TX_CHECKSUM_ERROR (1 << 15)
768#define TX_DSI_DATA_TYPE_NOT_RECOGNIZED (1 << 16)
769#define TX_DSI_VC_ID_INVALID (1 << 17)
770#define HIGH_CONTENTION (1 << 18)
771#define LOW_CONTENTION (1 << 19)
772#define DPI_FIFO_UNDER_RUN (1 << 20)
773#define HS_TX_TIMEOUT (1 << 21)
774#define LP_RX_TIMEOUT (1 << 22)
775#define TURN_AROUND_ACK_TIMEOUT (1 << 23)
776#define ACK_WITH_NO_ERROR (1 << 24)
777#define HS_GENERIC_WR_FIFO_FULL (1 << 27)
778#define LP_GENERIC_WR_FIFO_FULL (1 << 28)
779#define SPL_PKT_SENT (1 << 30)
780#define INTR_EN_REG 0xb008
781#define DSI_FUNC_PRG_REG 0xb00c
782#define DPI_CHANNEL_NUMBER_POS 0x03
783#define DBI_CHANNEL_NUMBER_POS 0x05
784#define FMT_DPI_POS 0x07
785#define FMT_DBI_POS 0x0A
786#define DBI_DATA_WIDTH_POS 0x0D
787
788/* DPI PIXEL FORMATS */
789#define RGB_565_FMT 0x01 /* RGB 565 FORMAT */
790#define RGB_666_FMT 0x02 /* RGB 666 FORMAT */
791#define LRGB_666_FMT 0x03 /* RGB LOOSELY PACKED
792 * 666 FORMAT
793 */
794#define RGB_888_FMT 0x04 /* RGB 888 FORMAT */
795#define VIRTUAL_CHANNEL_NUMBER_0 0x00 /* Virtual channel 0 */
796#define VIRTUAL_CHANNEL_NUMBER_1 0x01 /* Virtual channel 1 */
797#define VIRTUAL_CHANNEL_NUMBER_2 0x02 /* Virtual channel 2 */
798#define VIRTUAL_CHANNEL_NUMBER_3 0x03 /* Virtual channel 3 */
799
800#define DBI_NOT_SUPPORTED 0x00 /* command mode
801 * is not supported
802 */
803#define DBI_DATA_WIDTH_16BIT 0x01 /* 16 bit data */
804#define DBI_DATA_WIDTH_9BIT 0x02 /* 9 bit data */
805#define DBI_DATA_WIDTH_8BIT 0x03 /* 8 bit data */
806#define DBI_DATA_WIDTH_OPT1 0x04 /* option 1 */
807#define DBI_DATA_WIDTH_OPT2 0x05 /* option 2 */
808
809#define HS_TX_TIMEOUT_REG 0xb010
810#define LP_RX_TIMEOUT_REG 0xb014
811#define TURN_AROUND_TIMEOUT_REG 0xb018
812#define DEVICE_RESET_REG 0xb01C
813#define DPI_RESOLUTION_REG 0xb020
814#define RES_V_POS 0x10
815#define DBI_RESOLUTION_REG 0xb024 /* Reserved for MDFLD */
816#define HORIZ_SYNC_PAD_COUNT_REG 0xb028
817#define HORIZ_BACK_PORCH_COUNT_REG 0xb02C
818#define HORIZ_FRONT_PORCH_COUNT_REG 0xb030
819#define HORIZ_ACTIVE_AREA_COUNT_REG 0xb034
820#define VERT_SYNC_PAD_COUNT_REG 0xb038
821#define VERT_BACK_PORCH_COUNT_REG 0xb03c
822#define VERT_FRONT_PORCH_COUNT_REG 0xb040
823#define HIGH_LOW_SWITCH_COUNT_REG 0xb044
824#define DPI_CONTROL_REG 0xb048
825#define DPI_SHUT_DOWN (1 << 0)
826#define DPI_TURN_ON (1 << 1)
827#define DPI_COLOR_MODE_ON (1 << 2)
828#define DPI_COLOR_MODE_OFF (1 << 3)
829#define DPI_BACK_LIGHT_ON (1 << 4)
830#define DPI_BACK_LIGHT_OFF (1 << 5)
831#define DPI_LP (1 << 6)
832#define DPI_DATA_REG 0xb04c
833#define DPI_BACK_LIGHT_ON_DATA 0x07
834#define DPI_BACK_LIGHT_OFF_DATA 0x17
835#define INIT_COUNT_REG 0xb050
836#define MAX_RET_PAK_REG 0xb054
837#define VIDEO_FMT_REG 0xb058
838#define COMPLETE_LAST_PCKT (1 << 2)
839#define EOT_DISABLE_REG 0xb05c
840#define ENABLE_CLOCK_STOPPING (1 << 1)
841#define LP_BYTECLK_REG 0xb060
842#define LP_GEN_DATA_REG 0xb064
843#define HS_GEN_DATA_REG 0xb068
844#define LP_GEN_CTRL_REG 0xb06C
845#define HS_GEN_CTRL_REG 0xb070
846#define DCS_CHANNEL_NUMBER_POS 0x6
847#define MCS_COMMANDS_POS 0x8
848#define WORD_COUNTS_POS 0x8
849#define MCS_PARAMETER_POS 0x10
850#define GEN_FIFO_STAT_REG 0xb074
851#define HS_DATA_FIFO_FULL (1 << 0)
852#define HS_DATA_FIFO_HALF_EMPTY (1 << 1)
853#define HS_DATA_FIFO_EMPTY (1 << 2)
854#define LP_DATA_FIFO_FULL (1 << 8)
855#define LP_DATA_FIFO_HALF_EMPTY (1 << 9)
856#define LP_DATA_FIFO_EMPTY (1 << 10)
857#define HS_CTRL_FIFO_FULL (1 << 16)
858#define HS_CTRL_FIFO_HALF_EMPTY (1 << 17)
859#define HS_CTRL_FIFO_EMPTY (1 << 18)
860#define LP_CTRL_FIFO_FULL (1 << 24)
861#define LP_CTRL_FIFO_HALF_EMPTY (1 << 25)
862#define LP_CTRL_FIFO_EMPTY (1 << 26)
863#define DBI_FIFO_EMPTY (1 << 27)
864#define DPI_FIFO_EMPTY (1 << 28)
865#define HS_LS_DBI_ENABLE_REG 0xb078
866#define TXCLKESC_REG 0xb07c
867#define DPHY_PARAM_REG 0xb080
868#define DBI_BW_CTRL_REG 0xb084
869#define CLK_LANE_SWT_REG 0xb088
870
871/*
872 * MIPI Adapter registers
873 */
874#define MIPI_CONTROL_REG 0xb104
875#define MIPI_2X_CLOCK_BITS ((1 << 0) | (1 << 1))
876#define MIPI_DATA_ADDRESS_REG 0xb108
877#define MIPI_DATA_LENGTH_REG 0xb10C
878#define MIPI_COMMAND_ADDRESS_REG 0xb110
879#define MIPI_COMMAND_LENGTH_REG 0xb114
880#define MIPI_READ_DATA_RETURN_REG0 0xb118
881#define MIPI_READ_DATA_RETURN_REG1 0xb11C
882#define MIPI_READ_DATA_RETURN_REG2 0xb120
883#define MIPI_READ_DATA_RETURN_REG3 0xb124
884#define MIPI_READ_DATA_RETURN_REG4 0xb128
885#define MIPI_READ_DATA_RETURN_REG5 0xb12C
886#define MIPI_READ_DATA_RETURN_REG6 0xb130
887#define MIPI_READ_DATA_RETURN_REG7 0xb134
888#define MIPI_READ_DATA_VALID_REG 0xb138
889
890/* DBI COMMANDS */
891#define soft_reset 0x01
892/*
893 * The display module performs a software reset.
894 * Registers are written with their SW Reset default values.
895 */
896#define get_power_mode 0x0a
897/*
898 * The display module returns the current power mode
899 */
900#define get_address_mode 0x0b
901/*
902 * The display module returns the current status.
903 */
904#define get_pixel_format 0x0c
905/*
906 * This command gets the pixel format for the RGB image data
907 * used by the interface.
908 */
909#define get_display_mode 0x0d
910/*
911 * The display module returns the Display Image Mode status.
912 */
913#define get_signal_mode 0x0e
914/*
915 * The display module returns the Display Signal Mode.
916 */
917#define get_diagnostic_result 0x0f
918/*
919 * The display module returns the self-diagnostic results following
920 * a Sleep Out command.
921 */
922#define enter_sleep_mode 0x10
923/*
924 * This command causes the display module to enter the Sleep mode.
925 * In this mode, all unnecessary blocks inside the display module are
926 * disabled except interface communication. This is the lowest power
927 * mode the display module supports.
928 */
929#define exit_sleep_mode 0x11
930/*
931 * This command causes the display module to exit Sleep mode.
932 * All blocks inside the display module are enabled.
933 */
934#define enter_partial_mode 0x12
935/*
936 * This command causes the display module to enter the Partial Display
937 * Mode. The Partial Display Mode window is described by the
938 * set_partial_area command.
939 */
940#define enter_normal_mode 0x13
941/*
942 * This command causes the display module to enter the Normal mode.
943 * Normal Mode is defined as Partial Display mode and Scroll mode are off
944 */
945#define exit_invert_mode 0x20
946/*
947 * This command causes the display module to stop inverting the image
948 * data on the display device. The frame memory contents remain unchanged.
949 * No status bits are changed.
950 */
951#define enter_invert_mode 0x21
952/*
953 * This command causes the display module to invert the image data only on
954 * the display device. The frame memory contents remain unchanged.
955 * No status bits are changed.
956 */
957#define set_gamma_curve 0x26
958/*
959 * This command selects the desired gamma curve for the display device.
960 * Four fixed gamma curves are defined in section DCS spec.
961 */
962#define set_display_off 0x28
963/* ************************************************************************* *\
964This command causes the display module to stop displaying the image data
965on the display device. The frame memory contents remain unchanged.
966No status bits are changed.
967\* ************************************************************************* */
968#define set_display_on 0x29
969/* ************************************************************************* *\
970This command causes the display module to start displaying the image data
971on the display device. The frame memory contents remain unchanged.
972No status bits are changed.
973\* ************************************************************************* */
974#define set_column_address 0x2a
975/*
976 * This command defines the column extent of the frame memory accessed by
977 * the hostprocessor with the read_memory_continue and
978 * write_memory_continue commands.
979 * No status bits are changed.
980 */
981#define set_page_addr 0x2b
982/*
983 * This command defines the page extent of the frame memory accessed by
984 * the host processor with the write_memory_continue and
985 * read_memory_continue command.
986 * No status bits are changed.
987 */
988#define write_mem_start 0x2c
989/*
990 * This command transfers image data from the host processor to the
991 * display modules frame memory starting at the pixel location specified
992 * by preceding set_column_address and set_page_address commands.
993 */
994#define set_partial_area 0x30
995/*
996 * This command defines the Partial Display mode s display area.
997 * There are two parameters associated with this command, the first
998 * defines the Start Row (SR) and the second the End Row (ER). SR and ER
999 * refer to the Frame Memory Line Pointer.
1000 */
1001#define set_scroll_area 0x33
1002/*
1003 * This command defines the display modules Vertical Scrolling Area.
1004 */
1005#define set_tear_off 0x34
1006/*
1007 * This command turns off the display modules Tearing Effect output
1008 * signal on the TE signal line.
1009 */
1010#define set_tear_on 0x35
1011/*
1012 * This command turns on the display modules Tearing Effect output signal
1013 * on the TE signal line.
1014 */
1015#define set_address_mode 0x36
1016/*
1017 * This command sets the data order for transfers from the host processor
1018 * to display modules frame memory,bits B[7:5] and B3, and from the
1019 * display modules frame memory to the display device, bits B[2:0] and B4.
1020 */
1021#define set_scroll_start 0x37
1022/*
1023 * This command sets the start of the vertical scrolling area in the frame
1024 * memory. The vertical scrolling area is fully defined when this command
1025 * is used with the set_scroll_area command The set_scroll_start command
1026 * has one parameter, the Vertical Scroll Pointer. The VSP defines the
1027 * line in the frame memory that is written to the display device as the
1028 * first line of the vertical scroll area.
1029 */
1030#define exit_idle_mode 0x38
1031/*
1032 * This command causes the display module to exit Idle mode.
1033 */
1034#define enter_idle_mode 0x39
1035/*
1036 * This command causes the display module to enter Idle Mode.
1037 * In Idle Mode, color expression is reduced. Colors are shown on the
1038 * display device using the MSB of each of the R, G and B color
1039 * components in the frame memory
1040 */
1041#define set_pixel_format 0x3a
1042/*
1043 * This command sets the pixel format for the RGB image data used by the
1044 * interface.
1045 * Bits D[6:4] DPI Pixel Format Definition
1046 * Bits D[2:0] DBI Pixel Format Definition
1047 * Bits D7 and D3 are not used.
1048 */
1049#define DCS_PIXEL_FORMAT_3bpp 0x1
1050#define DCS_PIXEL_FORMAT_8bpp 0x2
1051#define DCS_PIXEL_FORMAT_12bpp 0x3
1052#define DCS_PIXEL_FORMAT_16bpp 0x5
1053#define DCS_PIXEL_FORMAT_18bpp 0x6
1054#define DCS_PIXEL_FORMAT_24bpp 0x7
1055
1056#define write_mem_cont 0x3c
1057
1058/*
1059 * This command transfers image data from the host processor to the
1060 * display module's frame memory continuing from the pixel location
1061 * following the previous write_memory_continue or write_memory_start
1062 * command.
1063 */
1064#define set_tear_scanline 0x44
1065/*
1066 * This command turns on the display modules Tearing Effect output signal
1067 * on the TE signal line when the display module reaches line N.
1068 */
1069#define get_scanline 0x45
1070/*
1071 * The display module returns the current scanline, N, used to update the
1072 * display device. The total number of scanlines on a display device is
1073 * defined as VSYNC + VBP + VACT + VFP.The first scanline is defined as
1074 * the first line of V Sync and is denoted as Line 0.
1075 * When in Sleep Mode, the value returned by get_scanline is undefined.
1076 */
1077
1078/* MCS or Generic COMMANDS */
1079/* MCS/generic data type */
1080#define GEN_SHORT_WRITE_0 0x03 /* generic short write, no parameters */
1081#define GEN_SHORT_WRITE_1 0x13 /* generic short write, 1 parameters */
1082#define GEN_SHORT_WRITE_2 0x23 /* generic short write, 2 parameters */
1083#define GEN_READ_0 0x04 /* generic read, no parameters */
1084#define GEN_READ_1 0x14 /* generic read, 1 parameters */
1085#define GEN_READ_2 0x24 /* generic read, 2 parameters */
1086#define GEN_LONG_WRITE 0x29 /* generic long write */
1087#define MCS_SHORT_WRITE_0 0x05 /* MCS short write, no parameters */
1088#define MCS_SHORT_WRITE_1 0x15 /* MCS short write, 1 parameters */
1089#define MCS_READ 0x06 /* MCS read, no parameters */
1090#define MCS_LONG_WRITE 0x39 /* MCS long write */
1091/* MCS/generic commands */
1092/* TPO MCS */
1093#define write_display_profile 0x50
1094#define write_display_brightness 0x51
1095#define write_ctrl_display 0x53
1096#define write_ctrl_cabc 0x55
1097 #define UI_IMAGE 0x01
1098 #define STILL_IMAGE 0x02
1099 #define MOVING_IMAGE 0x03
1100#define write_hysteresis 0x57
1101#define write_gamma_setting 0x58
1102#define write_cabc_min_bright 0x5e
1103#define write_kbbc_profile 0x60
1104/* TMD MCS */
1105#define tmd_write_display_brightness 0x8c
1106
1107/*
1108 * This command is used to control ambient light, panel backlight
1109 * brightness and gamma settings.
1110 */
1111#define BRIGHT_CNTL_BLOCK_ON (1 << 5)
1112#define AMBIENT_LIGHT_SENSE_ON (1 << 4)
1113#define DISPLAY_DIMMING_ON (1 << 3)
1114#define BACKLIGHT_ON (1 << 2)
1115#define DISPLAY_BRIGHTNESS_AUTO (1 << 1)
1116#define GAMMA_AUTO (1 << 0)
1117
1118/* DCS Interface Pixel Formats */
1119#define DCS_PIXEL_FORMAT_3BPP 0x1
1120#define DCS_PIXEL_FORMAT_8BPP 0x2
1121#define DCS_PIXEL_FORMAT_12BPP 0x3
1122#define DCS_PIXEL_FORMAT_16BPP 0x5
1123#define DCS_PIXEL_FORMAT_18BPP 0x6
1124#define DCS_PIXEL_FORMAT_24BPP 0x7
1125/* ONE PARAMETER READ DATA */
1126#define addr_mode_data 0xfc
1127#define diag_res_data 0x00
1128#define disp_mode_data 0x23
1129#define pxl_fmt_data 0x77
1130#define pwr_mode_data 0x74
1131#define sig_mode_data 0x00
1132/* TWO PARAMETERS READ DATA */
1133#define scanline_data1 0xff
1134#define scanline_data2 0xff
1135#define NON_BURST_MODE_SYNC_PULSE 0x01 /* Non Burst Mode
1136 * with Sync Pulse
1137 */
1138#define NON_BURST_MODE_SYNC_EVENTS 0x02 /* Non Burst Mode
1139 * with Sync events
1140 */
1141#define BURST_MODE 0x03 /* Burst Mode */
1142#define DBI_COMMAND_BUFFER_SIZE 0x240 /* 0x32 */ /* 0x120 */
1143 /* Allocate at least
1144 * 0x100 Byte with 32
1145 * byte alignment
1146 */
1147#define DBI_DATA_BUFFER_SIZE 0x120 /* Allocate at least
1148 * 0x100 Byte with 32
1149 * byte alignment
1150 */
1151#define DBI_CB_TIME_OUT 0xFFFF
1152
1153#define GEN_FB_TIME_OUT 2000
1154
1155#define SKU_83 0x01
1156#define SKU_100 0x02
1157#define SKU_100L 0x04
1158#define SKU_BYPASS 0x08
1159
1160/* Some handy macros for playing with bitfields. */
1161#define PSB_MASK(high, low) (((1<<((high)-(low)+1))-1)<<(low))
1162#define SET_FIELD(value, field) (((value) << field ## _SHIFT) & field ## _MASK)
1163#define GET_FIELD(word, field) (((word) & field ## _MASK) >> field ## _SHIFT)
1164
1165#define _PIPE(pipe, a, b) ((a) + (pipe)*((b)-(a)))
1166
1167/* PCI config space */
1168
1169#define SB_PCKT 0x02100 /* cedarview */
1170# define SB_OPCODE_MASK PSB_MASK(31, 16)
1171# define SB_OPCODE_SHIFT 16
1172# define SB_OPCODE_READ 0
1173# define SB_OPCODE_WRITE 1
1174# define SB_DEST_MASK PSB_MASK(15, 8)
1175# define SB_DEST_SHIFT 8
1176# define SB_DEST_DPLL 0x88
1177# define SB_BYTE_ENABLE_MASK PSB_MASK(7, 4)
1178# define SB_BYTE_ENABLE_SHIFT 4
1179# define SB_BUSY (1 << 0)
1180
1181
1182/* 32-bit value read/written from the DPIO reg. */
1183#define SB_DATA 0x02104 /* cedarview */
1184/* 32-bit address of the DPIO reg to be read/written. */
1185#define SB_ADDR 0x02108 /* cedarview */
1186#define DPIO_CFG 0x02110 /* cedarview */
1187# define DPIO_MODE_SELECT_1 (1 << 3)
1188# define DPIO_MODE_SELECT_0 (1 << 2)
1189# define DPIO_SFR_BYPASS (1 << 1)
1190/* reset is active low */
1191# define DPIO_CMN_RESET_N (1 << 0)
1192
1193/* Cedarview sideband registers */
1194#define _SB_M_A 0x8008
1195#define _SB_M_B 0x8028
1196#define SB_M(pipe) _PIPE(pipe, _SB_M_A, _SB_M_B)
1197# define SB_M_DIVIDER_MASK (0xFF << 24)
1198# define SB_M_DIVIDER_SHIFT 24
1199
1200#define _SB_N_VCO_A 0x8014
1201#define _SB_N_VCO_B 0x8034
1202#define SB_N_VCO(pipe) _PIPE(pipe, _SB_N_VCO_A, _SB_N_VCO_B)
1203#define SB_N_VCO_SEL_MASK PSB_MASK(31, 30)
1204#define SB_N_VCO_SEL_SHIFT 30
1205#define SB_N_DIVIDER_MASK PSB_MASK(29, 26)
1206#define SB_N_DIVIDER_SHIFT 26
1207#define SB_N_CB_TUNE_MASK PSB_MASK(25, 24)
1208#define SB_N_CB_TUNE_SHIFT 24
1209
1210#define _SB_REF_A 0x8018
1211#define _SB_REF_B 0x8038
1212#define SB_REF_SFR(pipe) _PIPE(pipe, _SB_REF_A, _SB_REF_B)
1213
1214#define _SB_P_A 0x801c
1215#define _SB_P_B 0x803c
1216#define SB_P(pipe) _PIPE(pipe, _SB_P_A, _SB_P_B)
1217#define SB_P2_DIVIDER_MASK PSB_MASK(31, 30)
1218#define SB_P2_DIVIDER_SHIFT 30
1219#define SB_P2_10 0 /* HDMI, DP, DAC */
1220#define SB_P2_5 1 /* DAC */
1221#define SB_P2_14 2 /* LVDS single */
1222#define SB_P2_7 3 /* LVDS double */
1223#define SB_P1_DIVIDER_MASK PSB_MASK(15, 12)
1224#define SB_P1_DIVIDER_SHIFT 12
1225
1226#define PSB_LANE0 0x120
1227#define PSB_LANE1 0x220
1228#define PSB_LANE2 0x2320
1229#define PSB_LANE3 0x2420
1230
1231#define LANE_PLL_MASK (0x7 << 20)
1232#define LANE_PLL_ENABLE (0x3 << 20)
1233
1234
1235#endif
diff --git a/drivers/gpu/drm/gma500/psb_intel_sdvo.c b/drivers/gpu/drm/gma500/psb_intel_sdvo.c
new file mode 100644
index 000000000000..a4bad1af4b7c
--- /dev/null
+++ b/drivers/gpu/drm/gma500/psb_intel_sdvo.c
@@ -0,0 +1,1293 @@
1/*
2 * Copyright (c) 2006-2007 Intel Corporation
3 *
4 * This program is free software; you can redistribute it and/or modify it
5 * under the terms and conditions of the GNU General Public License,
6 * version 2, as published by the Free Software Foundation.
7 *
8 * This program is distributed in the hope it will be useful, but WITHOUT
9 * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
10 * FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for
11 * more details.
12 *
13 * You should have received a copy of the GNU General Public License along with
14 * this program; if not, write to the Free Software Foundation, Inc.,
15 * 51 Franklin St - Fifth Floor, Boston, MA 02110-1301 USA.
16 *
17 * Authors:
18 * Eric Anholt <eric@anholt.net>
19 */
20
21#include <linux/i2c.h>
22#include <linux/delay.h>
23/* #include <drm/drm_crtc.h> */
24#include <drm/drmP.h>
25#include "psb_drv.h"
26#include "psb_intel_drv.h"
27#include "psb_intel_reg.h"
28#include "psb_intel_sdvo_regs.h"
29
30struct psb_intel_sdvo_priv {
31 struct psb_intel_i2c_chan *i2c_bus;
32 int slaveaddr;
33 int output_device;
34
35 u16 active_outputs;
36
37 struct psb_intel_sdvo_caps caps;
38 int pixel_clock_min, pixel_clock_max;
39
40 int save_sdvo_mult;
41 u16 save_active_outputs;
42 struct psb_intel_sdvo_dtd save_input_dtd_1, save_input_dtd_2;
43 struct psb_intel_sdvo_dtd save_output_dtd[16];
44 u32 save_SDVOX;
45 u8 in_out_map[4];
46
47 u8 by_input_wiring;
48 u32 active_device;
49};
50
51/**
52 * Writes the SDVOB or SDVOC with the given value, but always writes both
53 * SDVOB and SDVOC to work around apparent hardware issues (according to
54 * comments in the BIOS).
55 */
56void psb_intel_sdvo_write_sdvox(struct psb_intel_output *psb_intel_output,
57 u32 val)
58{
59 struct drm_device *dev = psb_intel_output->base.dev;
60 struct psb_intel_sdvo_priv *sdvo_priv = psb_intel_output->dev_priv;
61 u32 bval = val, cval = val;
62 int i;
63
64 if (sdvo_priv->output_device == SDVOB)
65 cval = REG_READ(SDVOC);
66 else
67 bval = REG_READ(SDVOB);
68 /*
69 * Write the registers twice for luck. Sometimes,
70 * writing them only once doesn't appear to 'stick'.
71 * The BIOS does this too. Yay, magic
72 */
73 for (i = 0; i < 2; i++) {
74 REG_WRITE(SDVOB, bval);
75 REG_READ(SDVOB);
76 REG_WRITE(SDVOC, cval);
77 REG_READ(SDVOC);
78 }
79}
80
81static bool psb_intel_sdvo_read_byte(
82 struct psb_intel_output *psb_intel_output,
83 u8 addr, u8 *ch)
84{
85 struct psb_intel_sdvo_priv *sdvo_priv = psb_intel_output->dev_priv;
86 u8 out_buf[2];
87 u8 buf[2];
88 int ret;
89
90 struct i2c_msg msgs[] = {
91 {
92 .addr = sdvo_priv->i2c_bus->slave_addr,
93 .flags = 0,
94 .len = 1,
95 .buf = out_buf,
96 },
97 {
98 .addr = sdvo_priv->i2c_bus->slave_addr,
99 .flags = I2C_M_RD,
100 .len = 1,
101 .buf = buf,
102 }
103 };
104
105 out_buf[0] = addr;
106 out_buf[1] = 0;
107
108 ret = i2c_transfer(&sdvo_priv->i2c_bus->adapter, msgs, 2);
109 if (ret == 2) {
110 *ch = buf[0];
111 return true;
112 }
113
114 return false;
115}
116
117static bool psb_intel_sdvo_write_byte(
118 struct psb_intel_output *psb_intel_output,
119 int addr, u8 ch)
120{
121 u8 out_buf[2];
122 struct i2c_msg msgs[] = {
123 {
124 .addr = psb_intel_output->i2c_bus->slave_addr,
125 .flags = 0,
126 .len = 2,
127 .buf = out_buf,
128 }
129 };
130
131 out_buf[0] = addr;
132 out_buf[1] = ch;
133
134 if (i2c_transfer(&psb_intel_output->i2c_bus->adapter, msgs, 1) == 1)
135 return true;
136 return false;
137}
138
139#define SDVO_CMD_NAME_ENTRY(cmd) {cmd, #cmd}
140/** Mapping of command numbers to names, for debug output */
141static const struct _sdvo_cmd_name {
142 u8 cmd;
143 char *name;
144} sdvo_cmd_names[] = {
145SDVO_CMD_NAME_ENTRY(SDVO_CMD_RESET),
146 SDVO_CMD_NAME_ENTRY(SDVO_CMD_GET_DEVICE_CAPS),
147 SDVO_CMD_NAME_ENTRY(SDVO_CMD_GET_FIRMWARE_REV),
148 SDVO_CMD_NAME_ENTRY(SDVO_CMD_GET_TRAINED_INPUTS),
149 SDVO_CMD_NAME_ENTRY(SDVO_CMD_GET_ACTIVE_OUTPUTS),
150 SDVO_CMD_NAME_ENTRY(SDVO_CMD_SET_ACTIVE_OUTPUTS),
151 SDVO_CMD_NAME_ENTRY(SDVO_CMD_GET_IN_OUT_MAP),
152 SDVO_CMD_NAME_ENTRY(SDVO_CMD_SET_IN_OUT_MAP),
153 SDVO_CMD_NAME_ENTRY(SDVO_CMD_GET_ATTACHED_DISPLAYS),
154 SDVO_CMD_NAME_ENTRY(SDVO_CMD_GET_HOT_PLUG_SUPPORT),
155 SDVO_CMD_NAME_ENTRY(SDVO_CMD_SET_ACTIVE_HOT_PLUG),
156 SDVO_CMD_NAME_ENTRY(SDVO_CMD_GET_ACTIVE_HOT_PLUG),
157 SDVO_CMD_NAME_ENTRY
158 (SDVO_CMD_GET_INTERRUPT_EVENT_SOURCE),
159 SDVO_CMD_NAME_ENTRY(SDVO_CMD_SET_TARGET_INPUT),
160 SDVO_CMD_NAME_ENTRY(SDVO_CMD_SET_TARGET_OUTPUT),
161 SDVO_CMD_NAME_ENTRY(SDVO_CMD_GET_INPUT_TIMINGS_PART1),
162 SDVO_CMD_NAME_ENTRY(SDVO_CMD_GET_INPUT_TIMINGS_PART2),
163 SDVO_CMD_NAME_ENTRY(SDVO_CMD_SET_INPUT_TIMINGS_PART1),
164 SDVO_CMD_NAME_ENTRY(SDVO_CMD_SET_INPUT_TIMINGS_PART2),
165 SDVO_CMD_NAME_ENTRY(SDVO_CMD_SET_INPUT_TIMINGS_PART1),
166 SDVO_CMD_NAME_ENTRY(SDVO_CMD_SET_OUTPUT_TIMINGS_PART1),
167 SDVO_CMD_NAME_ENTRY(SDVO_CMD_SET_OUTPUT_TIMINGS_PART2),
168 SDVO_CMD_NAME_ENTRY(SDVO_CMD_GET_OUTPUT_TIMINGS_PART1),
169 SDVO_CMD_NAME_ENTRY(SDVO_CMD_GET_OUTPUT_TIMINGS_PART2),
170 SDVO_CMD_NAME_ENTRY
171 (SDVO_CMD_CREATE_PREFERRED_INPUT_TIMING),
172 SDVO_CMD_NAME_ENTRY
173 (SDVO_CMD_GET_PREFERRED_INPUT_TIMING_PART1),
174 SDVO_CMD_NAME_ENTRY
175 (SDVO_CMD_GET_PREFERRED_INPUT_TIMING_PART2),
176 SDVO_CMD_NAME_ENTRY
177 (SDVO_CMD_GET_INPUT_PIXEL_CLOCK_RANGE),
178 SDVO_CMD_NAME_ENTRY
179 (SDVO_CMD_GET_OUTPUT_PIXEL_CLOCK_RANGE),
180 SDVO_CMD_NAME_ENTRY
181 (SDVO_CMD_GET_SUPPORTED_CLOCK_RATE_MULTS),
182 SDVO_CMD_NAME_ENTRY(SDVO_CMD_GET_CLOCK_RATE_MULT),
183 SDVO_CMD_NAME_ENTRY(SDVO_CMD_SET_CLOCK_RATE_MULT),
184 SDVO_CMD_NAME_ENTRY(SDVO_CMD_GET_SUPPORTED_TV_FORMATS),
185 SDVO_CMD_NAME_ENTRY(SDVO_CMD_GET_TV_FORMAT),
186 SDVO_CMD_NAME_ENTRY(SDVO_CMD_SET_TV_FORMAT),
187 SDVO_CMD_NAME_ENTRY
188 (SDVO_CMD_SET_TV_RESOLUTION_SUPPORT),
189 SDVO_CMD_NAME_ENTRY(SDVO_CMD_SET_CONTROL_BUS_SWITCH),};
190
191#define SDVO_NAME(dev_priv) \
192 ((dev_priv)->output_device == SDVOB ? "SDVOB" : "SDVOC")
193#define SDVO_PRIV(output) ((struct psb_intel_sdvo_priv *) (output)->dev_priv)
194
195static void psb_intel_sdvo_write_cmd(struct psb_intel_output *psb_intel_output,
196 u8 cmd,
197 void *args,
198 int args_len)
199{
200 struct psb_intel_sdvo_priv *sdvo_priv = psb_intel_output->dev_priv;
201 int i;
202
203 if (0) {
204 printk(KERN_DEBUG "%s: W: %02X ", SDVO_NAME(sdvo_priv), cmd);
205 for (i = 0; i < args_len; i++)
206 printk(KERN_CONT "%02X ", ((u8 *) args)[i]);
207 for (; i < 8; i++)
208 printk(KERN_CONT " ");
209 for (i = 0;
210 i <
211 sizeof(sdvo_cmd_names) / sizeof(sdvo_cmd_names[0]);
212 i++) {
213 if (cmd == sdvo_cmd_names[i].cmd) {
214 printk(KERN_CONT
215 "(%s)", sdvo_cmd_names[i].name);
216 break;
217 }
218 }
219 if (i ==
220 sizeof(sdvo_cmd_names) / sizeof(sdvo_cmd_names[0]))
221 printk(KERN_CONT "(%02X)", cmd);
222 printk(KERN_CONT "\n");
223 }
224
225 for (i = 0; i < args_len; i++) {
226 psb_intel_sdvo_write_byte(psb_intel_output,
227 SDVO_I2C_ARG_0 - i,
228 ((u8 *) args)[i]);
229 }
230
231 psb_intel_sdvo_write_byte(psb_intel_output, SDVO_I2C_OPCODE, cmd);
232}
233
234static const char *const cmd_status_names[] = {
235 "Power on",
236 "Success",
237 "Not supported",
238 "Invalid arg",
239 "Pending",
240 "Target not specified",
241 "Scaling not supported"
242};
243
244static u8 psb_intel_sdvo_read_response(
245 struct psb_intel_output *psb_intel_output,
246 void *response, int response_len)
247{
248 struct psb_intel_sdvo_priv *sdvo_priv = psb_intel_output->dev_priv;
249 int i;
250 u8 status;
251 u8 retry = 50;
252
253 while (retry--) {
254 /* Read the command response */
255 for (i = 0; i < response_len; i++) {
256 psb_intel_sdvo_read_byte(psb_intel_output,
257 SDVO_I2C_RETURN_0 + i,
258 &((u8 *) response)[i]);
259 }
260
261 /* read the return status */
262 psb_intel_sdvo_read_byte(psb_intel_output,
263 SDVO_I2C_CMD_STATUS,
264 &status);
265
266 if (0) {
267 pr_debug("%s: R: ", SDVO_NAME(sdvo_priv));
268 for (i = 0; i < response_len; i++)
269 printk(KERN_CONT "%02X ", ((u8 *) response)[i]);
270 for (; i < 8; i++)
271 printk(" ");
272 if (status <= SDVO_CMD_STATUS_SCALING_NOT_SUPP)
273 printk(KERN_CONT "(%s)",
274 cmd_status_names[status]);
275 else
276 printk(KERN_CONT "(??? %d)", status);
277 printk(KERN_CONT "\n");
278 }
279
280 if (status != SDVO_CMD_STATUS_PENDING)
281 return status;
282
283 mdelay(50);
284 }
285
286 return status;
287}
288
289int psb_intel_sdvo_get_pixel_multiplier(struct drm_display_mode *mode)
290{
291 if (mode->clock >= 100000)
292 return 1;
293 else if (mode->clock >= 50000)
294 return 2;
295 else
296 return 4;
297}
298
299/**
300 * Don't check status code from this as it switches the bus back to the
301 * SDVO chips which defeats the purpose of doing a bus switch in the first
302 * place.
303 */
304void psb_intel_sdvo_set_control_bus_switch(
305 struct psb_intel_output *psb_intel_output,
306 u8 target)
307{
308 psb_intel_sdvo_write_cmd(psb_intel_output,
309 SDVO_CMD_SET_CONTROL_BUS_SWITCH,
310 &target,
311 1);
312}
313
314static bool psb_intel_sdvo_set_target_input(
315 struct psb_intel_output *psb_intel_output,
316 bool target_0, bool target_1)
317{
318 struct psb_intel_sdvo_set_target_input_args targets = { 0 };
319 u8 status;
320
321 if (target_0 && target_1)
322 return SDVO_CMD_STATUS_NOTSUPP;
323
324 if (target_1)
325 targets.target_1 = 1;
326
327 psb_intel_sdvo_write_cmd(psb_intel_output, SDVO_CMD_SET_TARGET_INPUT,
328 &targets, sizeof(targets));
329
330 status = psb_intel_sdvo_read_response(psb_intel_output, NULL, 0);
331
332 return status == SDVO_CMD_STATUS_SUCCESS;
333}
334
335/**
336 * Return whether each input is trained.
337 *
338 * This function is making an assumption about the layout of the response,
339 * which should be checked against the docs.
340 */
341static bool psb_intel_sdvo_get_trained_inputs(struct psb_intel_output
342 *psb_intel_output, bool *input_1,
343 bool *input_2)
344{
345 struct psb_intel_sdvo_get_trained_inputs_response response;
346 u8 status;
347
348 psb_intel_sdvo_write_cmd(psb_intel_output, SDVO_CMD_GET_TRAINED_INPUTS,
349 NULL, 0);
350 status =
351 psb_intel_sdvo_read_response(psb_intel_output, &response,
352 sizeof(response));
353 if (status != SDVO_CMD_STATUS_SUCCESS)
354 return false;
355
356 *input_1 = response.input0_trained;
357 *input_2 = response.input1_trained;
358 return true;
359}
360
361static bool psb_intel_sdvo_get_active_outputs(struct psb_intel_output
362 *psb_intel_output, u16 *outputs)
363{
364 u8 status;
365
366 psb_intel_sdvo_write_cmd(psb_intel_output, SDVO_CMD_GET_ACTIVE_OUTPUTS,
367 NULL, 0);
368 status =
369 psb_intel_sdvo_read_response(psb_intel_output, outputs,
370 sizeof(*outputs));
371
372 return status == SDVO_CMD_STATUS_SUCCESS;
373}
374
375static bool psb_intel_sdvo_set_active_outputs(struct psb_intel_output
376 *psb_intel_output, u16 outputs)
377{
378 u8 status;
379
380 psb_intel_sdvo_write_cmd(psb_intel_output, SDVO_CMD_SET_ACTIVE_OUTPUTS,
381 &outputs, sizeof(outputs));
382 status = psb_intel_sdvo_read_response(psb_intel_output, NULL, 0);
383 return status == SDVO_CMD_STATUS_SUCCESS;
384}
385
386static bool psb_intel_sdvo_set_encoder_power_state(struct psb_intel_output
387 *psb_intel_output, int mode)
388{
389 u8 status, state = SDVO_ENCODER_STATE_ON;
390
391 switch (mode) {
392 case DRM_MODE_DPMS_ON:
393 state = SDVO_ENCODER_STATE_ON;
394 break;
395 case DRM_MODE_DPMS_STANDBY:
396 state = SDVO_ENCODER_STATE_STANDBY;
397 break;
398 case DRM_MODE_DPMS_SUSPEND:
399 state = SDVO_ENCODER_STATE_SUSPEND;
400 break;
401 case DRM_MODE_DPMS_OFF:
402 state = SDVO_ENCODER_STATE_OFF;
403 break;
404 }
405
406 psb_intel_sdvo_write_cmd(psb_intel_output,
407 SDVO_CMD_SET_ENCODER_POWER_STATE, &state,
408 sizeof(state));
409 status = psb_intel_sdvo_read_response(psb_intel_output, NULL, 0);
410
411 return status == SDVO_CMD_STATUS_SUCCESS;
412}
413
414static bool psb_intel_sdvo_get_input_pixel_clock_range(struct psb_intel_output
415 *psb_intel_output,
416 int *clock_min,
417 int *clock_max)
418{
419 struct psb_intel_sdvo_pixel_clock_range clocks;
420 u8 status;
421
422 psb_intel_sdvo_write_cmd(psb_intel_output,
423 SDVO_CMD_GET_INPUT_PIXEL_CLOCK_RANGE, NULL,
424 0);
425
426 status =
427 psb_intel_sdvo_read_response(psb_intel_output, &clocks,
428 sizeof(clocks));
429
430 if (status != SDVO_CMD_STATUS_SUCCESS)
431 return false;
432
433 /* Convert the values from units of 10 kHz to kHz. */
434 *clock_min = clocks.min * 10;
435 *clock_max = clocks.max * 10;
436
437 return true;
438}
439
440static bool psb_intel_sdvo_set_target_output(
441 struct psb_intel_output *psb_intel_output,
442 u16 outputs)
443{
444 u8 status;
445
446 psb_intel_sdvo_write_cmd(psb_intel_output, SDVO_CMD_SET_TARGET_OUTPUT,
447 &outputs, sizeof(outputs));
448
449 status = psb_intel_sdvo_read_response(psb_intel_output, NULL, 0);
450 return status == SDVO_CMD_STATUS_SUCCESS;
451}
452
453static bool psb_intel_sdvo_get_timing(struct psb_intel_output *psb_intel_output,
454 u8 cmd, struct psb_intel_sdvo_dtd *dtd)
455{
456 u8 status;
457
458 psb_intel_sdvo_write_cmd(psb_intel_output, cmd, NULL, 0);
459 status = psb_intel_sdvo_read_response(psb_intel_output, &dtd->part1,
460 sizeof(dtd->part1));
461 if (status != SDVO_CMD_STATUS_SUCCESS)
462 return false;
463
464 psb_intel_sdvo_write_cmd(psb_intel_output, cmd + 1, NULL, 0);
465 status = psb_intel_sdvo_read_response(psb_intel_output, &dtd->part2,
466 sizeof(dtd->part2));
467 if (status != SDVO_CMD_STATUS_SUCCESS)
468 return false;
469
470 return true;
471}
472
473static bool psb_intel_sdvo_get_input_timing(
474 struct psb_intel_output *psb_intel_output,
475 struct psb_intel_sdvo_dtd *dtd)
476{
477 return psb_intel_sdvo_get_timing(psb_intel_output,
478 SDVO_CMD_GET_INPUT_TIMINGS_PART1,
479 dtd);
480}
481
482static bool psb_intel_sdvo_set_timing(
483 struct psb_intel_output *psb_intel_output,
484 u8 cmd,
485 struct psb_intel_sdvo_dtd *dtd)
486{
487 u8 status;
488
489 psb_intel_sdvo_write_cmd(psb_intel_output, cmd, &dtd->part1,
490 sizeof(dtd->part1));
491 status = psb_intel_sdvo_read_response(psb_intel_output, NULL, 0);
492 if (status != SDVO_CMD_STATUS_SUCCESS)
493 return false;
494
495 psb_intel_sdvo_write_cmd(psb_intel_output, cmd + 1, &dtd->part2,
496 sizeof(dtd->part2));
497 status = psb_intel_sdvo_read_response(psb_intel_output, NULL, 0);
498 if (status != SDVO_CMD_STATUS_SUCCESS)
499 return false;
500
501 return true;
502}
503
504static bool psb_intel_sdvo_set_input_timing(
505 struct psb_intel_output *psb_intel_output,
506 struct psb_intel_sdvo_dtd *dtd)
507{
508 return psb_intel_sdvo_set_timing(psb_intel_output,
509 SDVO_CMD_SET_INPUT_TIMINGS_PART1,
510 dtd);
511}
512
513static bool psb_intel_sdvo_set_output_timing(
514 struct psb_intel_output *psb_intel_output,
515 struct psb_intel_sdvo_dtd *dtd)
516{
517 return psb_intel_sdvo_set_timing(psb_intel_output,
518 SDVO_CMD_SET_OUTPUT_TIMINGS_PART1,
519 dtd);
520}
521
522static int psb_intel_sdvo_get_clock_rate_mult(struct psb_intel_output
523 *psb_intel_output)
524{
525 u8 response, status;
526
527 psb_intel_sdvo_write_cmd(psb_intel_output,
528 SDVO_CMD_GET_CLOCK_RATE_MULT,
529 NULL,
530 0);
531
532 status = psb_intel_sdvo_read_response(psb_intel_output, &response, 1);
533
534 if (status != SDVO_CMD_STATUS_SUCCESS) {
535 DRM_DEBUG("Couldn't get SDVO clock rate multiplier\n");
536 return SDVO_CLOCK_RATE_MULT_1X;
537 } else {
538 DRM_DEBUG("Current clock rate multiplier: %d\n", response);
539 }
540
541 return response;
542}
543
544static bool psb_intel_sdvo_set_clock_rate_mult(struct psb_intel_output
545 *psb_intel_output, u8 val)
546{
547 u8 status;
548
549 psb_intel_sdvo_write_cmd(psb_intel_output,
550 SDVO_CMD_SET_CLOCK_RATE_MULT,
551 &val,
552 1);
553
554 status = psb_intel_sdvo_read_response(psb_intel_output, NULL, 0);
555 if (status != SDVO_CMD_STATUS_SUCCESS)
556 return false;
557
558 return true;
559}
560
561static bool psb_sdvo_set_current_inoutmap(struct psb_intel_output *output,
562 u32 in0outputmask,
563 u32 in1outputmask)
564{
565 u8 byArgs[4];
566 u8 status;
567 int i;
568 struct psb_intel_sdvo_priv *sdvo_priv = output->dev_priv;
569
570 /* Make all fields of the args/ret to zero */
571 memset(byArgs, 0, sizeof(byArgs));
572
573 /* Fill up the argument values; */
574 byArgs[0] = (u8) (in0outputmask & 0xFF);
575 byArgs[1] = (u8) ((in0outputmask >> 8) & 0xFF);
576 byArgs[2] = (u8) (in1outputmask & 0xFF);
577 byArgs[3] = (u8) ((in1outputmask >> 8) & 0xFF);
578
579
580 /*save inoutmap arg here*/
581 for (i = 0; i < 4; i++)
582 sdvo_priv->in_out_map[i] = byArgs[0];
583
584 psb_intel_sdvo_write_cmd(output, SDVO_CMD_SET_IN_OUT_MAP, byArgs, 4);
585 status = psb_intel_sdvo_read_response(output, NULL, 0);
586
587 if (status != SDVO_CMD_STATUS_SUCCESS)
588 return false;
589 return true;
590}
591
592
593static void psb_intel_sdvo_set_iomap(struct psb_intel_output *output)
594{
595 u32 dwCurrentSDVOIn0 = 0;
596 u32 dwCurrentSDVOIn1 = 0;
597 u32 dwDevMask = 0;
598
599
600 struct psb_intel_sdvo_priv *sdvo_priv = output->dev_priv;
601
602 /* Please DO NOT change the following code. */
603 /* SDVOB_IN0 or SDVOB_IN1 ==> sdvo_in0 */
604 /* SDVOC_IN0 or SDVOC_IN1 ==> sdvo_in1 */
605 if (sdvo_priv->by_input_wiring & (SDVOB_IN0 | SDVOC_IN0)) {
606 switch (sdvo_priv->active_device) {
607 case SDVO_DEVICE_LVDS:
608 dwDevMask = SDVO_OUTPUT_LVDS0 | SDVO_OUTPUT_LVDS1;
609 break;
610 case SDVO_DEVICE_TMDS:
611 dwDevMask = SDVO_OUTPUT_TMDS0 | SDVO_OUTPUT_TMDS1;
612 break;
613 case SDVO_DEVICE_TV:
614 dwDevMask =
615 SDVO_OUTPUT_YPRPB0 | SDVO_OUTPUT_SVID0 |
616 SDVO_OUTPUT_CVBS0 | SDVO_OUTPUT_YPRPB1 |
617 SDVO_OUTPUT_SVID1 | SDVO_OUTPUT_CVBS1 |
618 SDVO_OUTPUT_SCART0 | SDVO_OUTPUT_SCART1;
619 break;
620 case SDVO_DEVICE_CRT:
621 dwDevMask = SDVO_OUTPUT_RGB0 | SDVO_OUTPUT_RGB1;
622 break;
623 }
624 dwCurrentSDVOIn0 = (sdvo_priv->active_outputs & dwDevMask);
625 } else if (sdvo_priv->by_input_wiring & (SDVOB_IN1 | SDVOC_IN1)) {
626 switch (sdvo_priv->active_device) {
627 case SDVO_DEVICE_LVDS:
628 dwDevMask = SDVO_OUTPUT_LVDS0 | SDVO_OUTPUT_LVDS1;
629 break;
630 case SDVO_DEVICE_TMDS:
631 dwDevMask = SDVO_OUTPUT_TMDS0 | SDVO_OUTPUT_TMDS1;
632 break;
633 case SDVO_DEVICE_TV:
634 dwDevMask =
635 SDVO_OUTPUT_YPRPB0 | SDVO_OUTPUT_SVID0 |
636 SDVO_OUTPUT_CVBS0 | SDVO_OUTPUT_YPRPB1 |
637 SDVO_OUTPUT_SVID1 | SDVO_OUTPUT_CVBS1 |
638 SDVO_OUTPUT_SCART0 | SDVO_OUTPUT_SCART1;
639 break;
640 case SDVO_DEVICE_CRT:
641 dwDevMask = SDVO_OUTPUT_RGB0 | SDVO_OUTPUT_RGB1;
642 break;
643 }
644 dwCurrentSDVOIn1 = (sdvo_priv->active_outputs & dwDevMask);
645 }
646
647 psb_sdvo_set_current_inoutmap(output, dwCurrentSDVOIn0,
648 dwCurrentSDVOIn1);
649}
650
651
652static bool psb_intel_sdvo_mode_fixup(struct drm_encoder *encoder,
653 struct drm_display_mode *mode,
654 struct drm_display_mode *adjusted_mode)
655{
656 /* Make the CRTC code factor in the SDVO pixel multiplier. The SDVO
657 * device will be told of the multiplier during mode_set.
658 */
659 adjusted_mode->clock *= psb_intel_sdvo_get_pixel_multiplier(mode);
660 return true;
661}
662
663static void psb_intel_sdvo_mode_set(struct drm_encoder *encoder,
664 struct drm_display_mode *mode,
665 struct drm_display_mode *adjusted_mode)
666{
667 struct drm_device *dev = encoder->dev;
668 struct drm_crtc *crtc = encoder->crtc;
669 struct psb_intel_crtc *psb_intel_crtc = to_psb_intel_crtc(crtc);
670 struct psb_intel_output *psb_intel_output =
671 enc_to_psb_intel_output(encoder);
672 struct psb_intel_sdvo_priv *sdvo_priv = psb_intel_output->dev_priv;
673 u16 width, height;
674 u16 h_blank_len, h_sync_len, v_blank_len, v_sync_len;
675 u16 h_sync_offset, v_sync_offset;
676 u32 sdvox;
677 struct psb_intel_sdvo_dtd output_dtd;
678 int sdvo_pixel_multiply;
679
680 if (!mode)
681 return;
682
683 psb_intel_sdvo_set_target_output(psb_intel_output, 0);
684
685 width = mode->crtc_hdisplay;
686 height = mode->crtc_vdisplay;
687
688 /* do some mode translations */
689 h_blank_len = mode->crtc_hblank_end - mode->crtc_hblank_start;
690 h_sync_len = mode->crtc_hsync_end - mode->crtc_hsync_start;
691
692 v_blank_len = mode->crtc_vblank_end - mode->crtc_vblank_start;
693 v_sync_len = mode->crtc_vsync_end - mode->crtc_vsync_start;
694
695 h_sync_offset = mode->crtc_hsync_start - mode->crtc_hblank_start;
696 v_sync_offset = mode->crtc_vsync_start - mode->crtc_vblank_start;
697
698 output_dtd.part1.clock = mode->clock / 10;
699 output_dtd.part1.h_active = width & 0xff;
700 output_dtd.part1.h_blank = h_blank_len & 0xff;
701 output_dtd.part1.h_high = (((width >> 8) & 0xf) << 4) |
702 ((h_blank_len >> 8) & 0xf);
703 output_dtd.part1.v_active = height & 0xff;
704 output_dtd.part1.v_blank = v_blank_len & 0xff;
705 output_dtd.part1.v_high = (((height >> 8) & 0xf) << 4) |
706 ((v_blank_len >> 8) & 0xf);
707
708 output_dtd.part2.h_sync_off = h_sync_offset;
709 output_dtd.part2.h_sync_width = h_sync_len & 0xff;
710 output_dtd.part2.v_sync_off_width = (v_sync_offset & 0xf) << 4 |
711 (v_sync_len & 0xf);
712 output_dtd.part2.sync_off_width_high =
713 ((h_sync_offset & 0x300) >> 2) | ((h_sync_len & 0x300) >> 4) |
714 ((v_sync_offset & 0x30) >> 2) | ((v_sync_len & 0x30) >> 4);
715
716 output_dtd.part2.dtd_flags = 0x18;
717 if (mode->flags & DRM_MODE_FLAG_PHSYNC)
718 output_dtd.part2.dtd_flags |= 0x2;
719 if (mode->flags & DRM_MODE_FLAG_PVSYNC)
720 output_dtd.part2.dtd_flags |= 0x4;
721
722 output_dtd.part2.sdvo_flags = 0;
723 output_dtd.part2.v_sync_off_high = v_sync_offset & 0xc0;
724 output_dtd.part2.reserved = 0;
725
726 /* Set the output timing to the screen */
727 psb_intel_sdvo_set_target_output(psb_intel_output,
728 sdvo_priv->active_outputs);
729
730 /* Set the input timing to the screen. Assume always input 0. */
731 psb_intel_sdvo_set_target_input(psb_intel_output, true, false);
732
733 psb_intel_sdvo_set_output_timing(psb_intel_output, &output_dtd);
734
735 /* We would like to use i830_sdvo_create_preferred_input_timing() to
736 * provide the device with a timing it can support, if it supports that
737 * feature. However, presumably we would need to adjust the CRTC to
738 * output the preferred timing, and we don't support that currently.
739 */
740 psb_intel_sdvo_set_input_timing(psb_intel_output, &output_dtd);
741
742 switch (psb_intel_sdvo_get_pixel_multiplier(mode)) {
743 case 1:
744 psb_intel_sdvo_set_clock_rate_mult(psb_intel_output,
745 SDVO_CLOCK_RATE_MULT_1X);
746 break;
747 case 2:
748 psb_intel_sdvo_set_clock_rate_mult(psb_intel_output,
749 SDVO_CLOCK_RATE_MULT_2X);
750 break;
751 case 4:
752 psb_intel_sdvo_set_clock_rate_mult(psb_intel_output,
753 SDVO_CLOCK_RATE_MULT_4X);
754 break;
755 }
756
757 /* Set the SDVO control regs. */
758 sdvox = REG_READ(sdvo_priv->output_device);
759 switch (sdvo_priv->output_device) {
760 case SDVOB:
761 sdvox &= SDVOB_PRESERVE_MASK;
762 break;
763 case SDVOC:
764 sdvox &= SDVOC_PRESERVE_MASK;
765 break;
766 }
767 sdvox |= (9 << 19) | SDVO_BORDER_ENABLE;
768 if (psb_intel_crtc->pipe == 1)
769 sdvox |= SDVO_PIPE_B_SELECT;
770
771 sdvo_pixel_multiply = psb_intel_sdvo_get_pixel_multiplier(mode);
772
773 psb_intel_sdvo_write_sdvox(psb_intel_output, sdvox);
774
775 psb_intel_sdvo_set_iomap(psb_intel_output);
776}
777
778static void psb_intel_sdvo_dpms(struct drm_encoder *encoder, int mode)
779{
780 struct drm_device *dev = encoder->dev;
781 struct psb_intel_output *psb_intel_output =
782 enc_to_psb_intel_output(encoder);
783 struct psb_intel_sdvo_priv *sdvo_priv = psb_intel_output->dev_priv;
784 u32 temp;
785
786 if (mode != DRM_MODE_DPMS_ON) {
787 psb_intel_sdvo_set_active_outputs(psb_intel_output, 0);
788 if (0)
789 psb_intel_sdvo_set_encoder_power_state(
790 psb_intel_output,
791 mode);
792
793 if (mode == DRM_MODE_DPMS_OFF) {
794 temp = REG_READ(sdvo_priv->output_device);
795 if ((temp & SDVO_ENABLE) != 0) {
796 psb_intel_sdvo_write_sdvox(psb_intel_output,
797 temp &
798 ~SDVO_ENABLE);
799 }
800 }
801 } else {
802 bool input1, input2;
803 int i;
804 u8 status;
805
806 temp = REG_READ(sdvo_priv->output_device);
807 if ((temp & SDVO_ENABLE) == 0)
808 psb_intel_sdvo_write_sdvox(psb_intel_output,
809 temp | SDVO_ENABLE);
810 for (i = 0; i < 2; i++)
811 psb_intel_wait_for_vblank(dev);
812
813 status =
814 psb_intel_sdvo_get_trained_inputs(psb_intel_output,
815 &input1,
816 &input2);
817
818
819 /* Warn if the device reported failure to sync.
820 * A lot of SDVO devices fail to notify of sync, but it's
821 * a given it the status is a success, we succeeded.
822 */
823 if (status == SDVO_CMD_STATUS_SUCCESS && !input1) {
824 DRM_DEBUG
825 ("First %s output reported failure to sync\n",
826 SDVO_NAME(sdvo_priv));
827 }
828
829 if (0)
830 psb_intel_sdvo_set_encoder_power_state(
831 psb_intel_output,
832 mode);
833 psb_intel_sdvo_set_active_outputs(psb_intel_output,
834 sdvo_priv->active_outputs);
835 }
836 return;
837}
838
839static void psb_intel_sdvo_save(struct drm_connector *connector)
840{
841 struct drm_device *dev = connector->dev;
842 struct psb_intel_output *psb_intel_output =
843 to_psb_intel_output(connector);
844 struct psb_intel_sdvo_priv *sdvo_priv = psb_intel_output->dev_priv;
845 /*int o;*/
846
847 sdvo_priv->save_sdvo_mult =
848 psb_intel_sdvo_get_clock_rate_mult(psb_intel_output);
849 psb_intel_sdvo_get_active_outputs(psb_intel_output,
850 &sdvo_priv->save_active_outputs);
851
852 if (sdvo_priv->caps.sdvo_inputs_mask & 0x1) {
853 psb_intel_sdvo_set_target_input(psb_intel_output,
854 true,
855 false);
856 psb_intel_sdvo_get_input_timing(psb_intel_output,
857 &sdvo_priv->save_input_dtd_1);
858 }
859
860 if (sdvo_priv->caps.sdvo_inputs_mask & 0x2) {
861 psb_intel_sdvo_set_target_input(psb_intel_output,
862 false,
863 true);
864 psb_intel_sdvo_get_input_timing(psb_intel_output,
865 &sdvo_priv->save_input_dtd_2);
866 }
867 sdvo_priv->save_SDVOX = REG_READ(sdvo_priv->output_device);
868
869 /*TODO: save the in_out_map state*/
870}
871
872static void psb_intel_sdvo_restore(struct drm_connector *connector)
873{
874 struct drm_device *dev = connector->dev;
875 struct psb_intel_output *psb_intel_output =
876 to_psb_intel_output(connector);
877 struct psb_intel_sdvo_priv *sdvo_priv = psb_intel_output->dev_priv;
878 /*int o;*/
879 int i;
880 bool input1, input2;
881 u8 status;
882
883 psb_intel_sdvo_set_active_outputs(psb_intel_output, 0);
884
885 if (sdvo_priv->caps.sdvo_inputs_mask & 0x1) {
886 psb_intel_sdvo_set_target_input(psb_intel_output, true, false);
887 psb_intel_sdvo_set_input_timing(psb_intel_output,
888 &sdvo_priv->save_input_dtd_1);
889 }
890
891 if (sdvo_priv->caps.sdvo_inputs_mask & 0x2) {
892 psb_intel_sdvo_set_target_input(psb_intel_output, false, true);
893 psb_intel_sdvo_set_input_timing(psb_intel_output,
894 &sdvo_priv->save_input_dtd_2);
895 }
896
897 psb_intel_sdvo_set_clock_rate_mult(psb_intel_output,
898 sdvo_priv->save_sdvo_mult);
899
900 REG_WRITE(sdvo_priv->output_device, sdvo_priv->save_SDVOX);
901
902 if (sdvo_priv->save_SDVOX & SDVO_ENABLE) {
903 for (i = 0; i < 2; i++)
904 psb_intel_wait_for_vblank(dev);
905 status =
906 psb_intel_sdvo_get_trained_inputs(psb_intel_output,
907 &input1,
908 &input2);
909 if (status == SDVO_CMD_STATUS_SUCCESS && !input1)
910 DRM_DEBUG
911 ("First %s output reported failure to sync\n",
912 SDVO_NAME(sdvo_priv));
913 }
914
915 psb_intel_sdvo_set_active_outputs(psb_intel_output,
916 sdvo_priv->save_active_outputs);
917
918 /*TODO: restore in_out_map*/
919 psb_intel_sdvo_write_cmd(psb_intel_output,
920 SDVO_CMD_SET_IN_OUT_MAP,
921 sdvo_priv->in_out_map,
922 4);
923
924 psb_intel_sdvo_read_response(psb_intel_output, NULL, 0);
925}
926
927static int psb_intel_sdvo_mode_valid(struct drm_connector *connector,
928 struct drm_display_mode *mode)
929{
930 struct psb_intel_output *psb_intel_output =
931 to_psb_intel_output(connector);
932 struct psb_intel_sdvo_priv *sdvo_priv = psb_intel_output->dev_priv;
933
934 if (mode->flags & DRM_MODE_FLAG_DBLSCAN)
935 return MODE_NO_DBLESCAN;
936
937 if (sdvo_priv->pixel_clock_min > mode->clock)
938 return MODE_CLOCK_LOW;
939
940 if (sdvo_priv->pixel_clock_max < mode->clock)
941 return MODE_CLOCK_HIGH;
942
943 return MODE_OK;
944}
945
946static bool psb_intel_sdvo_get_capabilities(
947 struct psb_intel_output *psb_intel_output,
948 struct psb_intel_sdvo_caps *caps)
949{
950 u8 status;
951
952 psb_intel_sdvo_write_cmd(psb_intel_output,
953 SDVO_CMD_GET_DEVICE_CAPS,
954 NULL,
955 0);
956 status = psb_intel_sdvo_read_response(psb_intel_output,
957 caps,
958 sizeof(*caps));
959 if (status != SDVO_CMD_STATUS_SUCCESS)
960 return false;
961
962 return true;
963}
964
965struct drm_connector *psb_intel_sdvo_find(struct drm_device *dev, int sdvoB)
966{
967 struct drm_connector *connector = NULL;
968 struct psb_intel_output *iout = NULL;
969 struct psb_intel_sdvo_priv *sdvo;
970
971 /* find the sdvo connector */
972 list_for_each_entry(connector, &dev->mode_config.connector_list,
973 head) {
974 iout = to_psb_intel_output(connector);
975
976 if (iout->type != INTEL_OUTPUT_SDVO)
977 continue;
978
979 sdvo = iout->dev_priv;
980
981 if (sdvo->output_device == SDVOB && sdvoB)
982 return connector;
983
984 if (sdvo->output_device == SDVOC && !sdvoB)
985 return connector;
986
987 }
988
989 return NULL;
990}
991
992int psb_intel_sdvo_supports_hotplug(struct drm_connector *connector)
993{
994 u8 response[2];
995 u8 status;
996 struct psb_intel_output *psb_intel_output;
997
998 if (!connector)
999 return 0;
1000
1001 psb_intel_output = to_psb_intel_output(connector);
1002
1003 psb_intel_sdvo_write_cmd(psb_intel_output,
1004 SDVO_CMD_GET_HOT_PLUG_SUPPORT,
1005 NULL,
1006 0);
1007 status = psb_intel_sdvo_read_response(psb_intel_output,
1008 &response,
1009 2);
1010
1011 if (response[0] != 0)
1012 return 1;
1013
1014 return 0;
1015}
1016
1017void psb_intel_sdvo_set_hotplug(struct drm_connector *connector, int on)
1018{
1019 u8 response[2];
1020 u8 status;
1021 struct psb_intel_output *psb_intel_output =
1022 to_psb_intel_output(connector);
1023
1024 psb_intel_sdvo_write_cmd(psb_intel_output,
1025 SDVO_CMD_GET_ACTIVE_HOT_PLUG,
1026 NULL,
1027 0);
1028 psb_intel_sdvo_read_response(psb_intel_output, &response, 2);
1029
1030 if (on) {
1031 psb_intel_sdvo_write_cmd(psb_intel_output,
1032 SDVO_CMD_GET_HOT_PLUG_SUPPORT, NULL,
1033 0);
1034 status = psb_intel_sdvo_read_response(psb_intel_output,
1035 &response,
1036 2);
1037
1038 psb_intel_sdvo_write_cmd(psb_intel_output,
1039 SDVO_CMD_SET_ACTIVE_HOT_PLUG,
1040 &response, 2);
1041 } else {
1042 response[0] = 0;
1043 response[1] = 0;
1044 psb_intel_sdvo_write_cmd(psb_intel_output,
1045 SDVO_CMD_SET_ACTIVE_HOT_PLUG,
1046 &response, 2);
1047 }
1048
1049 psb_intel_sdvo_write_cmd(psb_intel_output,
1050 SDVO_CMD_GET_ACTIVE_HOT_PLUG,
1051 NULL,
1052 0);
1053 psb_intel_sdvo_read_response(psb_intel_output, &response, 2);
1054}
1055
1056static enum drm_connector_status psb_intel_sdvo_detect(struct drm_connector
1057 *connector, bool force)
1058{
1059 u8 response[2];
1060 u8 status;
1061 struct psb_intel_output *psb_intel_output =
1062 to_psb_intel_output(connector);
1063
1064 psb_intel_sdvo_write_cmd(psb_intel_output,
1065 SDVO_CMD_GET_ATTACHED_DISPLAYS,
1066 NULL,
1067 0);
1068 status = psb_intel_sdvo_read_response(psb_intel_output, &response, 2);
1069
1070 DRM_DEBUG("SDVO response %d %d\n", response[0], response[1]);
1071 if ((response[0] != 0) || (response[1] != 0))
1072 return connector_status_connected;
1073 else
1074 return connector_status_disconnected;
1075}
1076
1077static int psb_intel_sdvo_get_modes(struct drm_connector *connector)
1078{
1079 struct psb_intel_output *psb_intel_output =
1080 to_psb_intel_output(connector);
1081
1082 /* set the bus switch and get the modes */
1083 psb_intel_sdvo_set_control_bus_switch(psb_intel_output,
1084 SDVO_CONTROL_BUS_DDC2);
1085 psb_intel_ddc_get_modes(psb_intel_output);
1086
1087 if (list_empty(&connector->probed_modes))
1088 return 0;
1089 return 1;
1090}
1091
1092static void psb_intel_sdvo_destroy(struct drm_connector *connector)
1093{
1094 struct psb_intel_output *psb_intel_output =
1095 to_psb_intel_output(connector);
1096
1097 if (psb_intel_output->i2c_bus)
1098 psb_intel_i2c_destroy(psb_intel_output->i2c_bus);
1099 drm_sysfs_connector_remove(connector);
1100 drm_connector_cleanup(connector);
1101 kfree(psb_intel_output);
1102}
1103
1104static const struct drm_encoder_helper_funcs psb_intel_sdvo_helper_funcs = {
1105 .dpms = psb_intel_sdvo_dpms,
1106 .mode_fixup = psb_intel_sdvo_mode_fixup,
1107 .prepare = psb_intel_encoder_prepare,
1108 .mode_set = psb_intel_sdvo_mode_set,
1109 .commit = psb_intel_encoder_commit,
1110};
1111
1112static const struct drm_connector_funcs psb_intel_sdvo_connector_funcs = {
1113 .dpms = drm_helper_connector_dpms,
1114 .save = psb_intel_sdvo_save,
1115 .restore = psb_intel_sdvo_restore,
1116 .detect = psb_intel_sdvo_detect,
1117 .fill_modes = drm_helper_probe_single_connector_modes,
1118 .destroy = psb_intel_sdvo_destroy,
1119};
1120
1121static const struct drm_connector_helper_funcs
1122 psb_intel_sdvo_connector_helper_funcs = {
1123 .get_modes = psb_intel_sdvo_get_modes,
1124 .mode_valid = psb_intel_sdvo_mode_valid,
1125 .best_encoder = psb_intel_best_encoder,
1126};
1127
1128void psb_intel_sdvo_enc_destroy(struct drm_encoder *encoder)
1129{
1130 drm_encoder_cleanup(encoder);
1131}
1132
1133static const struct drm_encoder_funcs psb_intel_sdvo_enc_funcs = {
1134 .destroy = psb_intel_sdvo_enc_destroy,
1135};
1136
1137
1138void psb_intel_sdvo_init(struct drm_device *dev, int output_device)
1139{
1140 struct drm_connector *connector;
1141 struct psb_intel_output *psb_intel_output;
1142 struct psb_intel_sdvo_priv *sdvo_priv;
1143 struct psb_intel_i2c_chan *i2cbus = NULL;
1144 int connector_type;
1145 u8 ch[0x40];
1146 int i;
1147 int encoder_type, output_id;
1148
1149 psb_intel_output =
1150 kcalloc(sizeof(struct psb_intel_output) +
1151 sizeof(struct psb_intel_sdvo_priv), 1, GFP_KERNEL);
1152 if (!psb_intel_output)
1153 return;
1154
1155 connector = &psb_intel_output->base;
1156
1157 drm_connector_init(dev, connector, &psb_intel_sdvo_connector_funcs,
1158 DRM_MODE_CONNECTOR_Unknown);
1159 drm_connector_helper_add(connector,
1160 &psb_intel_sdvo_connector_helper_funcs);
1161 sdvo_priv = (struct psb_intel_sdvo_priv *) (psb_intel_output + 1);
1162 psb_intel_output->type = INTEL_OUTPUT_SDVO;
1163
1164 connector->interlace_allowed = 0;
1165 connector->doublescan_allowed = 0;
1166
1167 /* setup the DDC bus. */
1168 if (output_device == SDVOB)
1169 i2cbus =
1170 psb_intel_i2c_create(dev, GPIOE, "SDVOCTRL_E for SDVOB");
1171 else
1172 i2cbus =
1173 psb_intel_i2c_create(dev, GPIOE, "SDVOCTRL_E for SDVOC");
1174
1175 if (!i2cbus)
1176 goto err_connector;
1177
1178 sdvo_priv->i2c_bus = i2cbus;
1179
1180 if (output_device == SDVOB) {
1181 output_id = 1;
1182 sdvo_priv->by_input_wiring = SDVOB_IN0;
1183 sdvo_priv->i2c_bus->slave_addr = 0x38;
1184 } else {
1185 output_id = 2;
1186 sdvo_priv->i2c_bus->slave_addr = 0x39;
1187 }
1188
1189 sdvo_priv->output_device = output_device;
1190 psb_intel_output->i2c_bus = i2cbus;
1191 psb_intel_output->dev_priv = sdvo_priv;
1192
1193
1194 /* Read the regs to test if we can talk to the device */
1195 for (i = 0; i < 0x40; i++) {
1196 if (!psb_intel_sdvo_read_byte(psb_intel_output, i, &ch[i])) {
1197 dev_dbg(dev->dev, "No SDVO device found on SDVO%c\n",
1198 output_device == SDVOB ? 'B' : 'C');
1199 goto err_i2c;
1200 }
1201 }
1202
1203 psb_intel_sdvo_get_capabilities(psb_intel_output, &sdvo_priv->caps);
1204
1205 memset(&sdvo_priv->active_outputs, 0,
1206 sizeof(sdvo_priv->active_outputs));
1207
1208 /* TODO, CVBS, SVID, YPRPB & SCART outputs. */
1209 if (sdvo_priv->caps.output_flags & SDVO_OUTPUT_RGB0) {
1210 sdvo_priv->active_outputs = SDVO_OUTPUT_RGB0;
1211 sdvo_priv->active_device = SDVO_DEVICE_CRT;
1212 connector->display_info.subpixel_order =
1213 SubPixelHorizontalRGB;
1214 encoder_type = DRM_MODE_ENCODER_DAC;
1215 connector_type = DRM_MODE_CONNECTOR_VGA;
1216 } else if (sdvo_priv->caps.output_flags & SDVO_OUTPUT_RGB1) {
1217 sdvo_priv->active_outputs = SDVO_OUTPUT_RGB1;
1218 sdvo_priv->active_outputs = SDVO_DEVICE_CRT;
1219 connector->display_info.subpixel_order =
1220 SubPixelHorizontalRGB;
1221 encoder_type = DRM_MODE_ENCODER_DAC;
1222 connector_type = DRM_MODE_CONNECTOR_VGA;
1223 } else if (sdvo_priv->caps.output_flags & SDVO_OUTPUT_TMDS0) {
1224 sdvo_priv->active_outputs = SDVO_OUTPUT_TMDS0;
1225 sdvo_priv->active_device = SDVO_DEVICE_TMDS;
1226 connector->display_info.subpixel_order =
1227 SubPixelHorizontalRGB;
1228 encoder_type = DRM_MODE_ENCODER_TMDS;
1229 connector_type = DRM_MODE_CONNECTOR_DVID;
1230 } else if (sdvo_priv->caps.output_flags & SDVO_OUTPUT_TMDS1) {
1231 sdvo_priv->active_outputs = SDVO_OUTPUT_TMDS1;
1232 sdvo_priv->active_device = SDVO_DEVICE_TMDS;
1233 connector->display_info.subpixel_order =
1234 SubPixelHorizontalRGB;
1235 encoder_type = DRM_MODE_ENCODER_TMDS;
1236 connector_type = DRM_MODE_CONNECTOR_DVID;
1237 } else {
1238 unsigned char bytes[2];
1239
1240 memcpy(bytes, &sdvo_priv->caps.output_flags, 2);
1241 dev_dbg(dev->dev, "%s: No active RGB or TMDS outputs (0x%02x%02x)\n",
1242 SDVO_NAME(sdvo_priv), bytes[0], bytes[1]);
1243 goto err_i2c;
1244 }
1245
1246 drm_encoder_init(dev, &psb_intel_output->enc, &psb_intel_sdvo_enc_funcs,
1247 encoder_type);
1248 drm_encoder_helper_add(&psb_intel_output->enc,
1249 &psb_intel_sdvo_helper_funcs);
1250 connector->connector_type = connector_type;
1251
1252 drm_mode_connector_attach_encoder(&psb_intel_output->base,
1253 &psb_intel_output->enc);
1254 drm_sysfs_connector_add(connector);
1255
1256 /* Set the input timing to the screen. Assume always input 0. */
1257 psb_intel_sdvo_set_target_input(psb_intel_output, true, false);
1258
1259 psb_intel_sdvo_get_input_pixel_clock_range(psb_intel_output,
1260 &sdvo_priv->pixel_clock_min,
1261 &sdvo_priv->
1262 pixel_clock_max);
1263
1264
1265 dev_dbg(dev->dev, "%s device VID/DID: %02X:%02X.%02X, "
1266 "clock range %dMHz - %dMHz, "
1267 "input 1: %c, input 2: %c, "
1268 "output 1: %c, output 2: %c\n",
1269 SDVO_NAME(sdvo_priv),
1270 sdvo_priv->caps.vendor_id, sdvo_priv->caps.device_id,
1271 sdvo_priv->caps.device_rev_id,
1272 sdvo_priv->pixel_clock_min / 1000,
1273 sdvo_priv->pixel_clock_max / 1000,
1274 (sdvo_priv->caps.sdvo_inputs_mask & 0x1) ? 'Y' : 'N',
1275 (sdvo_priv->caps.sdvo_inputs_mask & 0x2) ? 'Y' : 'N',
1276 /* check currently supported outputs */
1277 sdvo_priv->caps.output_flags &
1278 (SDVO_OUTPUT_TMDS0 | SDVO_OUTPUT_RGB0) ? 'Y' : 'N',
1279 sdvo_priv->caps.output_flags &
1280 (SDVO_OUTPUT_TMDS1 | SDVO_OUTPUT_RGB1) ? 'Y' : 'N');
1281
1282 psb_intel_output->ddc_bus = i2cbus;
1283
1284 return;
1285
1286err_i2c:
1287 psb_intel_i2c_destroy(psb_intel_output->i2c_bus);
1288err_connector:
1289 drm_connector_cleanup(connector);
1290 kfree(psb_intel_output);
1291
1292 return;
1293}
diff --git a/drivers/gpu/drm/gma500/psb_intel_sdvo_regs.h b/drivers/gpu/drm/gma500/psb_intel_sdvo_regs.h
new file mode 100644
index 000000000000..96862ea65aba
--- /dev/null
+++ b/drivers/gpu/drm/gma500/psb_intel_sdvo_regs.h
@@ -0,0 +1,338 @@
1/*
2 * SDVO command definitions and structures.
3 *
4 * Copyright (c) 2008, Intel Corporation
5 *
6 * This program is free software; you can redistribute it and/or modify it
7 * under the terms and conditions of the GNU General Public License,
8 * version 2, as published by the Free Software Foundation.
9 *
10 * This program is distributed in the hope it will be useful, but WITHOUT
11 * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
12 * FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for
13 * more details.
14 *
15 * You should have received a copy of the GNU General Public License along with
16 * this program; if not, write to the Free Software Foundation, Inc.,
17 * 51 Franklin St - Fifth Floor, Boston, MA 02110-1301 USA.
18 *
19 * Authors:
20 * Eric Anholt <eric@anholt.net>
21 */
22
23#define SDVO_OUTPUT_FIRST (0)
24#define SDVO_OUTPUT_TMDS0 (1 << 0)
25#define SDVO_OUTPUT_RGB0 (1 << 1)
26#define SDVO_OUTPUT_CVBS0 (1 << 2)
27#define SDVO_OUTPUT_SVID0 (1 << 3)
28#define SDVO_OUTPUT_YPRPB0 (1 << 4)
29#define SDVO_OUTPUT_SCART0 (1 << 5)
30#define SDVO_OUTPUT_LVDS0 (1 << 6)
31#define SDVO_OUTPUT_TMDS1 (1 << 8)
32#define SDVO_OUTPUT_RGB1 (1 << 9)
33#define SDVO_OUTPUT_CVBS1 (1 << 10)
34#define SDVO_OUTPUT_SVID1 (1 << 11)
35#define SDVO_OUTPUT_YPRPB1 (1 << 12)
36#define SDVO_OUTPUT_SCART1 (1 << 13)
37#define SDVO_OUTPUT_LVDS1 (1 << 14)
38#define SDVO_OUTPUT_LAST (14)
39
40struct psb_intel_sdvo_caps {
41 u8 vendor_id;
42 u8 device_id;
43 u8 device_rev_id;
44 u8 sdvo_version_major;
45 u8 sdvo_version_minor;
46 unsigned int sdvo_inputs_mask:2;
47 unsigned int smooth_scaling:1;
48 unsigned int sharp_scaling:1;
49 unsigned int up_scaling:1;
50 unsigned int down_scaling:1;
51 unsigned int stall_support:1;
52 unsigned int pad:1;
53 u16 output_flags;
54} __packed;
55
56/** This matches the EDID DTD structure, more or less */
57struct psb_intel_sdvo_dtd {
58 struct {
59 u16 clock; /**< pixel clock, in 10kHz units */
60 u8 h_active; /**< lower 8 bits (pixels) */
61 u8 h_blank; /**< lower 8 bits (pixels) */
62 u8 h_high; /**< upper 4 bits each h_active, h_blank */
63 u8 v_active; /**< lower 8 bits (lines) */
64 u8 v_blank; /**< lower 8 bits (lines) */
65 u8 v_high; /**< upper 4 bits each v_active, v_blank */
66 } part1;
67
68 struct {
69 u8 h_sync_off;
70 /**< lower 8 bits, from hblank start */
71 u8 h_sync_width;/**< lower 8 bits (pixels) */
72 /** lower 4 bits each vsync offset, vsync width */
73 u8 v_sync_off_width;
74 /**
75 * 2 high bits of hsync offset, 2 high bits of hsync width,
76 * bits 4-5 of vsync offset, and 2 high bits of vsync width.
77 */
78 u8 sync_off_width_high;
79 u8 dtd_flags;
80 u8 sdvo_flags;
81 /** bits 6-7 of vsync offset at bits 6-7 */
82 u8 v_sync_off_high;
83 u8 reserved;
84 } part2;
85} __packed;
86
87struct psb_intel_sdvo_pixel_clock_range {
88 u16 min; /**< pixel clock, in 10kHz units */
89 u16 max; /**< pixel clock, in 10kHz units */
90} __packed;
91
92struct psb_intel_sdvo_preferred_input_timing_args {
93 u16 clock;
94 u16 width;
95 u16 height;
96} __packed;
97
98/* I2C registers for SDVO */
99#define SDVO_I2C_ARG_0 0x07
100#define SDVO_I2C_ARG_1 0x06
101#define SDVO_I2C_ARG_2 0x05
102#define SDVO_I2C_ARG_3 0x04
103#define SDVO_I2C_ARG_4 0x03
104#define SDVO_I2C_ARG_5 0x02
105#define SDVO_I2C_ARG_6 0x01
106#define SDVO_I2C_ARG_7 0x00
107#define SDVO_I2C_OPCODE 0x08
108#define SDVO_I2C_CMD_STATUS 0x09
109#define SDVO_I2C_RETURN_0 0x0a
110#define SDVO_I2C_RETURN_1 0x0b
111#define SDVO_I2C_RETURN_2 0x0c
112#define SDVO_I2C_RETURN_3 0x0d
113#define SDVO_I2C_RETURN_4 0x0e
114#define SDVO_I2C_RETURN_5 0x0f
115#define SDVO_I2C_RETURN_6 0x10
116#define SDVO_I2C_RETURN_7 0x11
117#define SDVO_I2C_VENDOR_BEGIN 0x20
118
119/* Status results */
120#define SDVO_CMD_STATUS_POWER_ON 0x0
121#define SDVO_CMD_STATUS_SUCCESS 0x1
122#define SDVO_CMD_STATUS_NOTSUPP 0x2
123#define SDVO_CMD_STATUS_INVALID_ARG 0x3
124#define SDVO_CMD_STATUS_PENDING 0x4
125#define SDVO_CMD_STATUS_TARGET_NOT_SPECIFIED 0x5
126#define SDVO_CMD_STATUS_SCALING_NOT_SUPP 0x6
127
128/* SDVO commands, argument/result registers */
129
130#define SDVO_CMD_RESET 0x01
131
132/** Returns a struct psb_intel_sdvo_caps */
133#define SDVO_CMD_GET_DEVICE_CAPS 0x02
134
135#define SDVO_CMD_GET_FIRMWARE_REV 0x86
136# define SDVO_DEVICE_FIRMWARE_MINOR SDVO_I2C_RETURN_0
137# define SDVO_DEVICE_FIRMWARE_MAJOR SDVO_I2C_RETURN_1
138# define SDVO_DEVICE_FIRMWARE_PATCH SDVO_I2C_RETURN_2
139
140/**
141 * Reports which inputs are trained (managed to sync).
142 *
143 * Devices must have trained within 2 vsyncs of a mode change.
144 */
145#define SDVO_CMD_GET_TRAINED_INPUTS 0x03
146struct psb_intel_sdvo_get_trained_inputs_response {
147 unsigned int input0_trained:1;
148 unsigned int input1_trained:1;
149 unsigned int pad:6;
150} __packed;
151
152/** Returns a struct psb_intel_sdvo_output_flags of active outputs. */
153#define SDVO_CMD_GET_ACTIVE_OUTPUTS 0x04
154
155/**
156 * Sets the current set of active outputs.
157 *
158 * Takes a struct psb_intel_sdvo_output_flags.
159 * Must be preceded by a SET_IN_OUT_MAP
160 * on multi-output devices.
161 */
162#define SDVO_CMD_SET_ACTIVE_OUTPUTS 0x05
163
164/**
165 * Returns the current mapping of SDVO inputs to outputs on the device.
166 *
167 * Returns two struct psb_intel_sdvo_output_flags structures.
168 */
169#define SDVO_CMD_GET_IN_OUT_MAP 0x06
170
171/**
172 * Sets the current mapping of SDVO inputs to outputs on the device.
173 *
174 * Takes two struct i380_sdvo_output_flags structures.
175 */
176#define SDVO_CMD_SET_IN_OUT_MAP 0x07
177
178/**
179 * Returns a struct psb_intel_sdvo_output_flags of attached displays.
180 */
181#define SDVO_CMD_GET_ATTACHED_DISPLAYS 0x0b
182
183/**
184 * Returns a struct psb_intel_sdvo_ouptut_flags of displays supporting hot plugging.
185 */
186#define SDVO_CMD_GET_HOT_PLUG_SUPPORT 0x0c
187
188/**
189 * Takes a struct psb_intel_sdvo_output_flags.
190 */
191#define SDVO_CMD_SET_ACTIVE_HOT_PLUG 0x0d
192
193/**
194 * Returns a struct psb_intel_sdvo_output_flags of displays with hot plug
195 * interrupts enabled.
196 */
197#define SDVO_CMD_GET_ACTIVE_HOT_PLUG 0x0e
198
199#define SDVO_CMD_GET_INTERRUPT_EVENT_SOURCE 0x0f
200struct psb_intel_sdvo_get_interrupt_event_source_response {
201 u16 interrupt_status;
202 unsigned int ambient_light_interrupt:1;
203 unsigned int pad:7;
204} __packed;
205
206/**
207 * Selects which input is affected by future input commands.
208 *
209 * Commands affected include SET_INPUT_TIMINGS_PART[12],
210 * GET_INPUT_TIMINGS_PART[12], GET_PREFERRED_INPUT_TIMINGS_PART[12],
211 * GET_INPUT_PIXEL_CLOCK_RANGE, and CREATE_PREFERRED_INPUT_TIMINGS.
212 */
213#define SDVO_CMD_SET_TARGET_INPUT 0x10
214struct psb_intel_sdvo_set_target_input_args {
215 unsigned int target_1:1;
216 unsigned int pad:7;
217} __packed;
218
219/**
220 * Takes a struct psb_intel_sdvo_output_flags of which outputs are targeted by
221 * future output commands.
222 *
223 * Affected commands inclue SET_OUTPUT_TIMINGS_PART[12],
224 * GET_OUTPUT_TIMINGS_PART[12], and GET_OUTPUT_PIXEL_CLOCK_RANGE.
225 */
226#define SDVO_CMD_SET_TARGET_OUTPUT 0x11
227
228#define SDVO_CMD_GET_INPUT_TIMINGS_PART1 0x12
229#define SDVO_CMD_GET_INPUT_TIMINGS_PART2 0x13
230#define SDVO_CMD_SET_INPUT_TIMINGS_PART1 0x14
231#define SDVO_CMD_SET_INPUT_TIMINGS_PART2 0x15
232#define SDVO_CMD_SET_OUTPUT_TIMINGS_PART1 0x16
233#define SDVO_CMD_SET_OUTPUT_TIMINGS_PART2 0x17
234#define SDVO_CMD_GET_OUTPUT_TIMINGS_PART1 0x18
235#define SDVO_CMD_GET_OUTPUT_TIMINGS_PART2 0x19
236/* Part 1 */
237# define SDVO_DTD_CLOCK_LOW SDVO_I2C_ARG_0
238# define SDVO_DTD_CLOCK_HIGH SDVO_I2C_ARG_1
239# define SDVO_DTD_H_ACTIVE SDVO_I2C_ARG_2
240# define SDVO_DTD_H_BLANK SDVO_I2C_ARG_3
241# define SDVO_DTD_H_HIGH SDVO_I2C_ARG_4
242# define SDVO_DTD_V_ACTIVE SDVO_I2C_ARG_5
243# define SDVO_DTD_V_BLANK SDVO_I2C_ARG_6
244# define SDVO_DTD_V_HIGH SDVO_I2C_ARG_7
245/* Part 2 */
246# define SDVO_DTD_HSYNC_OFF SDVO_I2C_ARG_0
247# define SDVO_DTD_HSYNC_WIDTH SDVO_I2C_ARG_1
248# define SDVO_DTD_VSYNC_OFF_WIDTH SDVO_I2C_ARG_2
249# define SDVO_DTD_SYNC_OFF_WIDTH_HIGH SDVO_I2C_ARG_3
250# define SDVO_DTD_DTD_FLAGS SDVO_I2C_ARG_4
251# define SDVO_DTD_DTD_FLAG_INTERLACED (1 << 7)
252# define SDVO_DTD_DTD_FLAG_STEREO_MASK (3 << 5)
253# define SDVO_DTD_DTD_FLAG_INPUT_MASK (3 << 3)
254# define SDVO_DTD_DTD_FLAG_SYNC_MASK (3 << 1)
255# define SDVO_DTD_SDVO_FLAS SDVO_I2C_ARG_5
256# define SDVO_DTD_SDVO_FLAG_STALL (1 << 7)
257# define SDVO_DTD_SDVO_FLAG_CENTERED (0 << 6)
258# define SDVO_DTD_SDVO_FLAG_UPPER_LEFT (1 << 6)
259# define SDVO_DTD_SDVO_FLAG_SCALING_MASK (3 << 4)
260# define SDVO_DTD_SDVO_FLAG_SCALING_NONE (0 << 4)
261# define SDVO_DTD_SDVO_FLAG_SCALING_SHARP (1 << 4)
262# define SDVO_DTD_SDVO_FLAG_SCALING_SMOOTH (2 << 4)
263# define SDVO_DTD_VSYNC_OFF_HIGH SDVO_I2C_ARG_6
264
265/**
266 * Generates a DTD based on the given width, height, and flags.
267 *
268 * This will be supported by any device supporting scaling or interlaced
269 * modes.
270 */
271#define SDVO_CMD_CREATE_PREFERRED_INPUT_TIMING 0x1a
272# define SDVO_PREFERRED_INPUT_TIMING_CLOCK_LOW SDVO_I2C_ARG_0
273# define SDVO_PREFERRED_INPUT_TIMING_CLOCK_HIGH SDVO_I2C_ARG_1
274# define SDVO_PREFERRED_INPUT_TIMING_WIDTH_LOW SDVO_I2C_ARG_2
275# define SDVO_PREFERRED_INPUT_TIMING_WIDTH_HIGH SDVO_I2C_ARG_3
276# define SDVO_PREFERRED_INPUT_TIMING_HEIGHT_LOW SDVO_I2C_ARG_4
277# define SDVO_PREFERRED_INPUT_TIMING_HEIGHT_HIGH SDVO_I2C_ARG_5
278# define SDVO_PREFERRED_INPUT_TIMING_FLAGS SDVO_I2C_ARG_6
279# define SDVO_PREFERRED_INPUT_TIMING_FLAGS_INTERLACED (1 << 0)
280# define SDVO_PREFERRED_INPUT_TIMING_FLAGS_SCALED (1 << 1)
281
282#define SDVO_CMD_GET_PREFERRED_INPUT_TIMING_PART1 0x1b
283#define SDVO_CMD_GET_PREFERRED_INPUT_TIMING_PART2 0x1c
284
285/** Returns a struct psb_intel_sdvo_pixel_clock_range */
286#define SDVO_CMD_GET_INPUT_PIXEL_CLOCK_RANGE 0x1d
287/** Returns a struct psb_intel_sdvo_pixel_clock_range */
288#define SDVO_CMD_GET_OUTPUT_PIXEL_CLOCK_RANGE 0x1e
289
290/** Returns a byte bitfield containing SDVO_CLOCK_RATE_MULT_* flags */
291#define SDVO_CMD_GET_SUPPORTED_CLOCK_RATE_MULTS 0x1f
292
293/** Returns a byte containing a SDVO_CLOCK_RATE_MULT_* flag */
294#define SDVO_CMD_GET_CLOCK_RATE_MULT 0x20
295/** Takes a byte containing a SDVO_CLOCK_RATE_MULT_* flag */
296#define SDVO_CMD_SET_CLOCK_RATE_MULT 0x21
297# define SDVO_CLOCK_RATE_MULT_1X (1 << 0)
298# define SDVO_CLOCK_RATE_MULT_2X (1 << 1)
299# define SDVO_CLOCK_RATE_MULT_4X (1 << 3)
300
301#define SDVO_CMD_GET_SUPPORTED_TV_FORMATS 0x27
302
303#define SDVO_CMD_GET_TV_FORMAT 0x28
304
305#define SDVO_CMD_SET_TV_FORMAT 0x29
306
307#define SDVO_CMD_GET_SUPPORTED_POWER_STATES 0x2a
308#define SDVO_CMD_GET_ENCODER_POWER_STATE 0x2b
309#define SDVO_CMD_SET_ENCODER_POWER_STATE 0x2c
310# define SDVO_ENCODER_STATE_ON (1 << 0)
311# define SDVO_ENCODER_STATE_STANDBY (1 << 1)
312# define SDVO_ENCODER_STATE_SUSPEND (1 << 2)
313# define SDVO_ENCODER_STATE_OFF (1 << 3)
314
315#define SDVO_CMD_SET_TV_RESOLUTION_SUPPORT 0x93
316
317#define SDVO_CMD_SET_CONTROL_BUS_SWITCH 0x7a
318# define SDVO_CONTROL_BUS_PROM 0x0
319# define SDVO_CONTROL_BUS_DDC1 0x1
320# define SDVO_CONTROL_BUS_DDC2 0x2
321# define SDVO_CONTROL_BUS_DDC3 0x3
322
323/* SDVO Bus & SDVO Inputs wiring details*/
324/* Bit 0: Is SDVOB connected to In0 (1 = yes, 0 = no*/
325/* Bit 1: Is SDVOB connected to In1 (1 = yes, 0 = no*/
326/* Bit 2: Is SDVOC connected to In0 (1 = yes, 0 = no*/
327/* Bit 3: Is SDVOC connected to In1 (1 = yes, 0 = no*/
328#define SDVOB_IN0 0x01
329#define SDVOB_IN1 0x02
330#define SDVOC_IN0 0x04
331#define SDVOC_IN1 0x08
332
333#define SDVO_DEVICE_NONE 0x00
334#define SDVO_DEVICE_CRT 0x01
335#define SDVO_DEVICE_TV 0x02
336#define SDVO_DEVICE_LVDS 0x04
337#define SDVO_DEVICE_TMDS 0x08
338
diff --git a/drivers/gpu/drm/gma500/psb_lid.c b/drivers/gpu/drm/gma500/psb_lid.c
new file mode 100644
index 000000000000..af328516561e
--- /dev/null
+++ b/drivers/gpu/drm/gma500/psb_lid.c
@@ -0,0 +1,90 @@
1/**************************************************************************
2 * Copyright (c) 2007, Intel Corporation.
3 *
4 * This program is free software; you can redistribute it and/or modify it
5 * under the terms and conditions of the GNU General Public License,
6 * version 2, as published by the Free Software Foundation.
7 *
8 * This program is distributed in the hope it will be useful, but WITHOUT
9 * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
10 * FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for
11 * more details.
12 *
13 * You should have received a copy of the GNU General Public License along with
14 * this program; if not, write to the Free Software Foundation, Inc.,
15 * 51 Franklin St - Fifth Floor, Boston, MA 02110-1301 USA.
16 *
17 * Authors: Thomas Hellstrom <thomas-at-tungstengraphics-dot-com>
18 **************************************************************************/
19
20#include <drm/drmP.h>
21#include "psb_drv.h"
22#include "psb_reg.h"
23#include "psb_intel_reg.h"
24#include <linux/spinlock.h>
25
26static void psb_lid_timer_func(unsigned long data)
27{
28 struct drm_psb_private * dev_priv = (struct drm_psb_private *)data;
29 struct drm_device *dev = (struct drm_device *)dev_priv->dev;
30 struct timer_list *lid_timer = &dev_priv->lid_timer;
31 unsigned long irq_flags;
32 u32 *lid_state = dev_priv->lid_state;
33 u32 pp_status;
34
35 if (readl(lid_state) == dev_priv->lid_last_state)
36 goto lid_timer_schedule;
37
38 if ((readl(lid_state)) & 0x01) {
39 /*lid state is open*/
40 REG_WRITE(PP_CONTROL, REG_READ(PP_CONTROL) | POWER_TARGET_ON);
41 do {
42 pp_status = REG_READ(PP_STATUS);
43 } while ((pp_status & PP_ON) == 0);
44
45 /*FIXME: should be backlight level before*/
46 psb_intel_lvds_set_brightness(dev, 100);
47 } else {
48 psb_intel_lvds_set_brightness(dev, 0);
49
50 REG_WRITE(PP_CONTROL, REG_READ(PP_CONTROL) & ~POWER_TARGET_ON);
51 do {
52 pp_status = REG_READ(PP_STATUS);
53 } while ((pp_status & PP_ON) == 0);
54 }
55 /* printk(KERN_INFO"%s: lid: closed\n", __FUNCTION__); */
56
57 dev_priv->lid_last_state = readl(lid_state);
58
59lid_timer_schedule:
60 spin_lock_irqsave(&dev_priv->lid_lock, irq_flags);
61 if (!timer_pending(lid_timer)) {
62 lid_timer->expires = jiffies + PSB_LID_DELAY;
63 add_timer(lid_timer);
64 }
65 spin_unlock_irqrestore(&dev_priv->lid_lock, irq_flags);
66}
67
68void psb_lid_timer_init(struct drm_psb_private *dev_priv)
69{
70 struct timer_list *lid_timer = &dev_priv->lid_timer;
71 unsigned long irq_flags;
72
73 spin_lock_init(&dev_priv->lid_lock);
74 spin_lock_irqsave(&dev_priv->lid_lock, irq_flags);
75
76 init_timer(lid_timer);
77
78 lid_timer->data = (unsigned long)dev_priv;
79 lid_timer->function = psb_lid_timer_func;
80 lid_timer->expires = jiffies + PSB_LID_DELAY;
81
82 add_timer(lid_timer);
83 spin_unlock_irqrestore(&dev_priv->lid_lock, irq_flags);
84}
85
86void psb_lid_timer_takedown(struct drm_psb_private *dev_priv)
87{
88 del_timer_sync(&dev_priv->lid_timer);
89}
90