aboutsummaryrefslogtreecommitdiffstats
path: root/drivers/gpu/drm/i915/intel_i2c.c
diff options
context:
space:
mode:
authorChris Wilson <chris@chris-wilson.co.uk>2010-07-20 18:44:45 -0400
committerChris Wilson <chris@chris-wilson.co.uk>2010-09-18 10:46:19 -0400
commitf899fc64cda8569d0529452aafc0da31c042df2e (patch)
tree61b6d32abe3524b83abc9d8b9382e3f82225cd64 /drivers/gpu/drm/i915/intel_i2c.c
parent373a3cf744c774478f44921c50011b896ab08f9d (diff)
drm/i915: use GMBUS to manage i2c links
Use the GMBUS interface rather than direct bit banging to grab the EDID over DDC (and for other forms of auxiliary communication with external display controllers). The hope is that this method will be much faster and more reliable than bit banging for fetching EDIDs from buggy monitors or through switches, though we still preserve the bit banging as a fallback in case GMBUS fails. Based on an original patch by Jesse Barnes. Cc: Jesse Barnes <jbarnes@virtuousgeek.org> Signed-off-by: Chris Wilson <chris@chris-wilson.co.uk>
Diffstat (limited to 'drivers/gpu/drm/i915/intel_i2c.c')
-rw-r--r--drivers/gpu/drm/i915/intel_i2c.c381
1 files changed, 268 insertions, 113 deletions
diff --git a/drivers/gpu/drm/i915/intel_i2c.c b/drivers/gpu/drm/i915/intel_i2c.c
index d3d65a9cfba1..6f4d128935ac 100644
--- a/drivers/gpu/drm/i915/intel_i2c.c
+++ b/drivers/gpu/drm/i915/intel_i2c.c
@@ -1,6 +1,6 @@
1/* 1/*
2 * Copyright (c) 2006 Dave Airlie <airlied@linux.ie> 2 * Copyright (c) 2006 Dave Airlie <airlied@linux.ie>
3 * Copyright © 2006-2008 Intel Corporation 3 * Copyright © 2006-2008,2010 Intel Corporation
4 * Jesse Barnes <jesse.barnes@intel.com> 4 * Jesse Barnes <jesse.barnes@intel.com>
5 * 5 *
6 * Permission is hereby granted, free of charge, to any person obtaining a 6 * Permission is hereby granted, free of charge, to any person obtaining a
@@ -24,10 +24,9 @@
24 * 24 *
25 * Authors: 25 * Authors:
26 * Eric Anholt <eric@anholt.net> 26 * Eric Anholt <eric@anholt.net>
27 * Chris Wilson <chris@chris-wilson.co.uk>
27 */ 28 */
28#include <linux/i2c.h> 29#include <linux/i2c.h>
29#include <linux/slab.h>
30#include <linux/i2c-id.h>
31#include <linux/i2c-algo-bit.h> 30#include <linux/i2c-algo-bit.h>
32#include "drmP.h" 31#include "drmP.h"
33#include "drm.h" 32#include "drm.h"
@@ -35,13 +34,33 @@
35#include "i915_drm.h" 34#include "i915_drm.h"
36#include "i915_drv.h" 35#include "i915_drv.h"
37 36
38void intel_i2c_quirk_set(struct drm_device *dev, bool enable) 37/* Intel GPIO access functions */
38
39#define I2C_RISEFALL_TIME 20
40
41struct intel_gpio {
42 struct i2c_adapter adapter;
43 struct i2c_algo_bit_data algo;
44 struct drm_i915_private *dev_priv;
45 u32 reg;
46};
47
48void
49intel_i2c_reset(struct drm_device *dev)
39{ 50{
40 struct drm_i915_private *dev_priv = dev->dev_private; 51 struct drm_i915_private *dev_priv = dev->dev_private;
52 if (HAS_PCH_SPLIT(dev))
53 I915_WRITE(PCH_GMBUS0, 0);
54 else
55 I915_WRITE(GMBUS0, 0);
56}
57
58static void intel_i2c_quirk_set(struct drm_i915_private *dev_priv, bool enable)
59{
41 u32 val; 60 u32 val;
42 61
43 /* When using bit bashing for I2C, this bit needs to be set to 1 */ 62 /* When using bit bashing for I2C, this bit needs to be set to 1 */
44 if (!IS_PINEVIEW(dev)) 63 if (!IS_PINEVIEW(dev_priv->dev))
45 return; 64 return;
46 65
47 val = I915_READ(DSPCLK_GATE_D); 66 val = I915_READ(DSPCLK_GATE_D);
@@ -52,42 +71,30 @@ void intel_i2c_quirk_set(struct drm_device *dev, bool enable)
52 I915_WRITE(DSPCLK_GATE_D, val); 71 I915_WRITE(DSPCLK_GATE_D, val);
53} 72}
54 73
55/*
56 * Intel GPIO access functions
57 */
58
59#define I2C_RISEFALL_TIME 20
60
61static inline struct drm_i915_private *
62get_dev_priv(struct intel_i2c_chan *chan)
63{
64 return chan->encoder->base.dev->dev_private;
65}
66
67static int get_clock(void *data) 74static int get_clock(void *data)
68{ 75{
69 struct intel_i2c_chan *chan = data; 76 struct intel_gpio *gpio = data;
70 struct drm_i915_private *dev_priv = get_dev_priv(chan); 77 struct drm_i915_private *dev_priv = gpio->dev_priv;
71 return (I915_READ(chan->reg) & GPIO_CLOCK_VAL_IN) != 0; 78 return (I915_READ(gpio->reg) & GPIO_CLOCK_VAL_IN) != 0;
72} 79}
73 80
74static int get_data(void *data) 81static int get_data(void *data)
75{ 82{
76 struct intel_i2c_chan *chan = data; 83 struct intel_gpio *gpio = data;
77 struct drm_i915_private *dev_priv = get_dev_priv(chan); 84 struct drm_i915_private *dev_priv = gpio->dev_priv;
78 return (I915_READ(chan->reg) & GPIO_DATA_VAL_IN) != 0; 85 return (I915_READ(gpio->reg) & GPIO_DATA_VAL_IN) != 0;
79} 86}
80 87
81static void set_clock(void *data, int state_high) 88static void set_clock(void *data, int state_high)
82{ 89{
83 struct intel_i2c_chan *chan = data; 90 struct intel_gpio *gpio = data;
84 struct drm_i915_private *dev_priv = get_dev_priv(chan); 91 struct drm_i915_private *dev_priv = gpio->dev_priv;
85 struct drm_device *dev = dev_priv->dev; 92 struct drm_device *dev = dev_priv->dev;
86 u32 reserved = 0, clock_bits; 93 u32 reserved = 0, clock_bits;
87 94
88 /* On most chips, these bits must be preserved in software. */ 95 /* On most chips, these bits must be preserved in software. */
89 if (!IS_I830(dev) && !IS_845G(dev)) 96 if (!IS_I830(dev) && !IS_845G(dev))
90 reserved = I915_READ(chan->reg) & (GPIO_DATA_PULLUP_DISABLE | 97 reserved = I915_READ(gpio->reg) & (GPIO_DATA_PULLUP_DISABLE |
91 GPIO_CLOCK_PULLUP_DISABLE); 98 GPIO_CLOCK_PULLUP_DISABLE);
92 99
93 if (state_high) 100 if (state_high)
@@ -95,20 +102,21 @@ static void set_clock(void *data, int state_high)
95 else 102 else
96 clock_bits = GPIO_CLOCK_DIR_OUT | GPIO_CLOCK_DIR_MASK | 103 clock_bits = GPIO_CLOCK_DIR_OUT | GPIO_CLOCK_DIR_MASK |
97 GPIO_CLOCK_VAL_MASK; 104 GPIO_CLOCK_VAL_MASK;
98 I915_WRITE(chan->reg, reserved | clock_bits); 105
99 POSTING_READ(chan->reg); 106 I915_WRITE(gpio->reg, reserved | clock_bits);
107 POSTING_READ(gpio->reg);
100} 108}
101 109
102static void set_data(void *data, int state_high) 110static void set_data(void *data, int state_high)
103{ 111{
104 struct intel_i2c_chan *chan = data; 112 struct intel_gpio *gpio = data;
105 struct drm_i915_private *dev_priv = get_dev_priv(chan); 113 struct drm_i915_private *dev_priv = gpio->dev_priv;
106 struct drm_device *dev = dev_priv->dev; 114 struct drm_device *dev = dev_priv->dev;
107 u32 reserved = 0, data_bits; 115 u32 reserved = 0, data_bits;
108 116
109 /* On most chips, these bits must be preserved in software. */ 117 /* On most chips, these bits must be preserved in software. */
110 if (!IS_I830(dev) && !IS_845G(dev)) 118 if (!IS_I830(dev) && !IS_845G(dev))
111 reserved = I915_READ(chan->reg) & (GPIO_DATA_PULLUP_DISABLE | 119 reserved = I915_READ(gpio->reg) & (GPIO_DATA_PULLUP_DISABLE |
112 GPIO_CLOCK_PULLUP_DISABLE); 120 GPIO_CLOCK_PULLUP_DISABLE);
113 121
114 if (state_high) 122 if (state_high)
@@ -117,111 +125,258 @@ static void set_data(void *data, int state_high)
117 data_bits = GPIO_DATA_DIR_OUT | GPIO_DATA_DIR_MASK | 125 data_bits = GPIO_DATA_DIR_OUT | GPIO_DATA_DIR_MASK |
118 GPIO_DATA_VAL_MASK; 126 GPIO_DATA_VAL_MASK;
119 127
120 I915_WRITE(chan->reg, reserved | data_bits); 128 I915_WRITE(gpio->reg, reserved | data_bits);
121 POSTING_READ(chan->reg); 129 POSTING_READ(gpio->reg);
122} 130}
123 131
124/* Clears the GMBUS setup. Our driver doesn't make use of the GMBUS I2C 132static struct i2c_adapter *
125 * engine, but if the BIOS leaves it enabled, then that can break our use 133intel_gpio_create(struct drm_i915_private *dev_priv, u32 pin)
126 * of the bit-banging I2C interfaces. This is notably the case with the
127 * Mac Mini in EFI mode.
128 */
129void
130intel_i2c_reset_gmbus(struct drm_device *dev)
131{ 134{
132 struct drm_i915_private *dev_priv = dev->dev_private; 135 static const int map_pin_to_reg[] = {
136 0,
137 GPIOB,
138 GPIOA,
139 GPIOC,
140 GPIOD,
141 GPIOE,
142 GPIOF,
143 };
144 struct intel_gpio *gpio;
133 145
134 if (HAS_PCH_SPLIT(dev)) 146 if (pin < 1 || pin > 7)
135 I915_WRITE(PCH_GMBUS0, 0); 147 return NULL;
136 else
137 I915_WRITE(GMBUS0, 0);
138}
139 148
140/** 149 gpio = kzalloc(sizeof(struct intel_gpio), GFP_KERNEL);
141 * intel_i2c_create - instantiate an Intel i2c bus using the specified GPIO reg 150 if (gpio == NULL)
142 * @dev: DRM device 151 return NULL;
143 * @output: driver specific output device
144 * @reg: GPIO reg to use
145 * @name: name for this bus
146 * @slave_addr: slave address (if fixed)
147 *
148 * Creates and registers a new i2c bus with the Linux i2c layer, for use
149 * in output probing and control (e.g. DDC or SDVO control functions).
150 *
151 * Possible values for @reg include:
152 * %GPIOA
153 * %GPIOB
154 * %GPIOC
155 * %GPIOD
156 * %GPIOE
157 * %GPIOF
158 * %GPIOG
159 * %GPIOH
160 * see PRM for details on how these different busses are used.
161 */
162struct i2c_adapter *intel_i2c_create(struct intel_encoder *encoder,
163 const u32 reg,
164 const char *name)
165{
166 struct intel_i2c_chan *chan;
167 struct drm_device *dev = encoder->base.dev;
168 152
169 chan = kzalloc(sizeof(struct intel_i2c_chan), GFP_KERNEL); 153 gpio->reg = map_pin_to_reg[pin];
170 if (!chan) 154 if (HAS_PCH_SPLIT(dev_priv->dev))
171 goto out_free; 155 gpio->reg += PCH_GPIOA - GPIOA;
156 gpio->dev_priv = dev_priv;
172 157
173 chan->encoder = encoder; 158 snprintf(gpio->adapter.name, I2C_NAME_SIZE, "GPIO %d", pin);
174 chan->reg = reg; 159 gpio->adapter.owner = THIS_MODULE;
175 snprintf(chan->adapter.name, I2C_NAME_SIZE, "intel drm %s", name); 160 gpio->adapter.algo_data = &gpio->algo;
176 chan->adapter.owner = THIS_MODULE; 161 gpio->adapter.dev.parent = &dev_priv->dev->pdev->dev;
177 chan->adapter.algo_data = &chan->algo; 162 gpio->algo.setsda = set_data;
178 chan->adapter.dev.parent = &dev->pdev->dev; 163 gpio->algo.setscl = set_clock;
179 chan->algo.setsda = set_data; 164 gpio->algo.getsda = get_data;
180 chan->algo.setscl = set_clock; 165 gpio->algo.getscl = get_clock;
181 chan->algo.getsda = get_data; 166 gpio->algo.udelay = I2C_RISEFALL_TIME;
182 chan->algo.getscl = get_clock; 167 gpio->algo.timeout = usecs_to_jiffies(2200);
183 chan->algo.udelay = I2C_RISEFALL_TIME; 168 gpio->algo.data = gpio;
184 chan->algo.timeout = usecs_to_jiffies(2200); 169
185 chan->algo.data = chan; 170 if (i2c_bit_add_bus(&gpio->adapter))
186
187 i2c_set_adapdata(&chan->adapter, chan);
188
189 if (i2c_bit_add_bus(&chan->adapter))
190 goto out_free; 171 goto out_free;
191 172
192 intel_i2c_reset_gmbus(dev); 173 intel_i2c_reset(dev_priv->dev);
193 174
194 /* JJJ: raise SCL and SDA? */ 175 /* JJJ: raise SCL and SDA? */
195 intel_i2c_quirk_set(dev, true); 176 intel_i2c_quirk_set(dev_priv, true);
196 set_data(chan, 1); 177 set_data(gpio, 1);
197 udelay(I2C_RISEFALL_TIME); 178 udelay(I2C_RISEFALL_TIME);
198 set_clock(chan, 1); 179 set_clock(gpio, 1);
199 udelay(I2C_RISEFALL_TIME); 180 udelay(I2C_RISEFALL_TIME);
200 intel_i2c_quirk_set(dev, false); 181 intel_i2c_quirk_set(dev_priv, false);
201 182
202 return &chan->adapter; 183 return &gpio->adapter;
203 184
204out_free: 185out_free:
205 kfree(chan); 186 kfree(gpio);
206 return NULL; 187 return NULL;
207} 188}
208 189
190static int
191quirk_i2c_transfer(struct drm_i915_private *dev_priv,
192 struct i2c_adapter *adapter,
193 struct i2c_msg *msgs,
194 int num)
195{
196 int ret;
197
198 intel_i2c_reset(dev_priv->dev);
199
200 intel_i2c_quirk_set(dev_priv, true);
201 ret = i2c_transfer(adapter, msgs, num);
202 intel_i2c_quirk_set(dev_priv, false);
203
204 return ret;
205}
206
207static int
208gmbus_xfer(struct i2c_adapter *adapter,
209 struct i2c_msg *msgs,
210 int num)
211{
212 struct intel_gmbus *bus = container_of(adapter,
213 struct intel_gmbus,
214 adapter);
215 struct drm_i915_private *dev_priv = adapter->algo_data;
216 int i, speed, reg_offset;
217
218 if (bus->force_bitbanging)
219 return quirk_i2c_transfer(dev_priv, bus->force_bitbanging, msgs, num);
220
221 reg_offset = HAS_PCH_SPLIT(dev_priv->dev) ? PCH_GMBUS0 - GMBUS0 : 0;
222
223 speed = GMBUS_RATE_100KHZ;
224 if (INTEL_INFO(dev_priv->dev)->gen > 4 || IS_G4X(dev_priv->dev)) {
225 if (bus->pin == GMBUS_PORT_DPB) /* SDVO only? */
226 speed = GMBUS_RATE_1MHZ;
227 else
228 speed = GMBUS_RATE_400KHZ;
229 }
230 I915_WRITE(GMBUS0 + reg_offset, speed | bus->pin);
231
232 for (i = 0; i < num; i++) {
233 u16 len = msgs[i].len;
234 u8 *buf = msgs[i].buf;
235
236 if (msgs[i].flags & I2C_M_RD) {
237 I915_WRITE(GMBUS1 + reg_offset,
238 GMBUS_CYCLE_WAIT | (i + 1 == num ? GMBUS_CYCLE_STOP : 0) |
239 (len << GMBUS_BYTE_COUNT_SHIFT) |
240 (msgs[i].addr << GMBUS_SLAVE_ADDR_SHIFT) |
241 GMBUS_SLAVE_READ | GMBUS_SW_RDY);
242 do {
243 u32 val, loop = 0;
244
245 if (wait_for(I915_READ(GMBUS2 + reg_offset) & (GMBUS_SATOER | GMBUS_HW_RDY), 50))
246 goto timeout;
247 if (I915_READ(GMBUS2 + reg_offset) & GMBUS_SATOER)
248 return 0;
249
250 val = I915_READ(GMBUS3 + reg_offset);
251 do {
252 *buf++ = val & 0xff;
253 val >>= 8;
254 } while (--len && ++loop < 4);
255 } while (len);
256 } else {
257 u32 val = 0, loop = 0;
258
259 BUG_ON(msgs[i].len > 4);
260
261 do {
262 val |= *buf++ << (loop*8);
263 } while (--len && +loop < 4);
264
265 I915_WRITE(GMBUS3 + reg_offset, val);
266 I915_WRITE(GMBUS1 + reg_offset,
267 (i + 1 == num ? GMBUS_CYCLE_STOP : GMBUS_CYCLE_WAIT ) |
268 (msgs[i].len << GMBUS_BYTE_COUNT_SHIFT) |
269 (msgs[i].addr << GMBUS_SLAVE_ADDR_SHIFT) |
270 GMBUS_SLAVE_WRITE | GMBUS_SW_RDY);
271 }
272
273 if (i + 1 < num && wait_for(I915_READ(GMBUS2 + reg_offset) & (GMBUS_SATOER | GMBUS_HW_WAIT_PHASE), 50))
274 goto timeout;
275 if (I915_READ(GMBUS2 + reg_offset) & GMBUS_SATOER)
276 return 0;
277 }
278
279 return num;
280
281timeout:
282 DRM_INFO("GMBUS timed out, falling back to bit banging on pin %d\n", bus->pin);
283 /* Hardware may not support GMBUS over these pins? Try GPIO bitbanging instead. */
284 bus->force_bitbanging = intel_gpio_create(dev_priv, bus->pin);
285 if (!bus->force_bitbanging)
286 return -ENOMEM;
287
288 return quirk_i2c_transfer(dev_priv, bus->force_bitbanging, msgs, num);
289}
290
291static u32 gmbus_func(struct i2c_adapter *adapter)
292{
293 return (I2C_FUNC_I2C | I2C_FUNC_SMBUS_EMUL |
294 /* I2C_FUNC_10BIT_ADDR | */
295 I2C_FUNC_SMBUS_READ_BLOCK_DATA |
296 I2C_FUNC_SMBUS_BLOCK_PROC_CALL);
297}
298
299static const struct i2c_algorithm gmbus_algorithm = {
300 .master_xfer = gmbus_xfer,
301 .functionality = gmbus_func
302};
303
209/** 304/**
210 * intel_i2c_destroy - unregister and free i2c bus resources 305 * intel_gmbus_setup - instantiate all Intel i2c GMBuses
211 * @output: channel to free 306 * @dev: DRM device
212 *
213 * Unregister the adapter from the i2c layer, then free the structure.
214 */ 307 */
215void intel_i2c_destroy(struct i2c_adapter *adapter) 308int intel_setup_gmbus(struct drm_device *dev)
309{
310 static const char *names[] = {
311 "disabled",
312 "ssc",
313 "vga",
314 "panel",
315 "dpc",
316 "dpb",
317 "dpd",
318 "reserved"
319 };
320 struct drm_i915_private *dev_priv = dev->dev_private;
321 int ret, i;
322
323 dev_priv->gmbus = kcalloc(sizeof(struct intel_gmbus), GMBUS_NUM_PORTS,
324 GFP_KERNEL);
325 if (dev_priv->gmbus == NULL)
326 return -ENOMEM;
327
328 for (i = 0; i < GMBUS_NUM_PORTS; i++) {
329 struct intel_gmbus *bus = &dev_priv->gmbus[i];
330
331 bus->adapter.owner = THIS_MODULE;
332 bus->adapter.class = I2C_CLASS_DDC;
333 snprintf(bus->adapter.name,
334 I2C_NAME_SIZE,
335 "gmbus %s",
336 names[i]);
337
338 bus->adapter.dev.parent = &dev->pdev->dev;
339 bus->adapter.algo_data = dev_priv;
340
341 bus->adapter.algo = &gmbus_algorithm;
342 ret = i2c_add_adapter(&bus->adapter);
343 if (ret)
344 goto err;
345
346 bus->pin = i;
347 }
348
349 intel_i2c_reset(dev_priv->dev);
350
351 return 0;
352
353err:
354 while (--i) {
355 struct intel_gmbus *bus = &dev_priv->gmbus[i];
356 i2c_del_adapter(&bus->adapter);
357 }
358 kfree(dev_priv->gmbus);
359 dev_priv->gmbus = NULL;
360 return ret;
361}
362
363void intel_teardown_gmbus(struct drm_device *dev)
216{ 364{
217 struct intel_i2c_chan *chan; 365 struct drm_i915_private *dev_priv = dev->dev_private;
366 int i;
218 367
219 if (!adapter) 368 if (dev_priv->gmbus == NULL)
220 return; 369 return;
221 370
222 chan = container_of(adapter, 371 for (i = 0; i < GMBUS_NUM_PORTS; i++) {
223 struct intel_i2c_chan, 372 struct intel_gmbus *bus = &dev_priv->gmbus[i];
224 adapter); 373 if (bus->force_bitbanging) {
225 i2c_del_adapter(&chan->adapter); 374 i2c_del_adapter(bus->force_bitbanging);
226 kfree(chan); 375 kfree(bus->force_bitbanging);
376 }
377 i2c_del_adapter(&bus->adapter);
378 }
379
380 kfree(dev_priv->gmbus);
381 dev_priv->gmbus = NULL;
227} 382}