Message ID | 5171034E.1020204@elsoft.ch (mailing list archive) |
---|---|
State | New, archived |
Headers | show |
On Fri, Apr 19, 2013 at 10:41:50AM +0200, "David Müller (ELSOFT AG)" wrote: > Hello > > As discussed in this thread > http://lists.freedesktop.org/archives/dri-devel/2013-April/037411.html > GMBUS based DVO transmitter detection seems to be unreliable which could > result in an unusable DVO port. > > The attached patch fixes this by falling back to bit banging mode for > the time DVO transmitter detection is in progress. > > Signed-off-by: David Müller <d.mueller@elsoft.ch> > Tested-by: David Müller <d.mueller@elsoft.ch> > > --- > diff -dpurN a/drivers/gpu/drm/i915/intel_dvo.c b/drivers/gpu/drm/i915/intel_dvo.c > --- a/drivers/gpu/drm/i915/intel_dvo.c 2012-12-11 10:09:35.113446850 +0100 > +++ b/drivers/gpu/drm/i915/intel_dvo.c 2013-04-19 07:21:54.054546365 +0200 > @@ -449,6 +449,7 @@ void intel_dvo_init(struct drm_device *d > const struct intel_dvo_device *dvo = &intel_dvo_devices[i]; > struct i2c_adapter *i2c; > int gpio; > + bool dvoinit; > > /* Allow the I2C driver info to specify the GPIO to be used in > * special cases, but otherwise default to what's defined > @@ -468,7 +469,17 @@ void intel_dvo_init(struct drm_device *d > i2c = intel_gmbus_get_adapter(dev_priv, gpio); > > intel_dvo->dev = *dvo; > - if (!dvo->dev_ops->init(&intel_dvo->dev, i2c)) > + > + /* GMBUS NAK handling seems to be unstable, hence let the > + * transmitter detection run in bit banging mode for now. > + */ > + intel_gmbus_force_bit(i2c, true); > + > + dvoinit = dvo->dev_ops->init(&intel_dvo->dev, i2c); > + > + intel_gmbus_force_bit(i2c, false); Shouldn't we keep the dvo i2c line in bit-banging mode always, i.e. restore gmbus mode only when dvo init failed? I suspect that for fickle hw not just init will fail ... -Daniel > + > + if (!dvoinit) > continue; > > intel_encoder->type = INTEL_OUTPUT_DVO;
Daniel Vetter wrote: > On Fri, Apr 19, 2013 at 10:41:50AM +0200, "David Müller (ELSOFT AG)" wrote: >> + /* GMBUS NAK handling seems to be unstable, hence let the >> + * transmitter detection run in bit banging mode for now. >> + */ >> + intel_gmbus_force_bit(i2c, true); >> + >> + dvoinit = dvo->dev_ops->init(&intel_dvo->dev, i2c); >> + >> + intel_gmbus_force_bit(i2c, false); > > Shouldn't we keep the dvo i2c line in bit-banging mode always, i.e. > restore gmbus mode only when dvo init failed? > > I suspect that for fickle hw not just init will fail ... As far as i can tell, the critical part is the NAK handling. Dave
On Fri, Apr 19, 2013 at 12:54:00PM +0200, "David Müller (ELSOFT AG)" wrote: > Daniel Vetter wrote: > > On Fri, Apr 19, 2013 at 10:41:50AM +0200, "David Müller (ELSOFT AG)" wrote: > >> + /* GMBUS NAK handling seems to be unstable, hence let the > >> + * transmitter detection run in bit banging mode for now. > >> + */ > >> + intel_gmbus_force_bit(i2c, true); > >> + > >> + dvoinit = dvo->dev_ops->init(&intel_dvo->dev, i2c); > >> + > >> + intel_gmbus_force_bit(i2c, false); > > > > Shouldn't we keep the dvo i2c line in bit-banging mode always, i.e. > > restore gmbus mode only when dvo init failed? > > > > I suspect that for fickle hw not just init will fail ... > > As far as i can tell, the critical part is the NAK handling. Ok, I've merged the patch for 3.10 with cc: stable. Thanks, Daniel
diff -dpurN a/drivers/gpu/drm/i915/intel_dvo.c b/drivers/gpu/drm/i915/intel_dvo.c --- a/drivers/gpu/drm/i915/intel_dvo.c 2012-12-11 10:09:35.113446850 +0100 +++ b/drivers/gpu/drm/i915/intel_dvo.c 2013-04-19 07:21:54.054546365 +0200 @@ -449,6 +449,7 @@ void intel_dvo_init(struct drm_device *d const struct intel_dvo_device *dvo = &intel_dvo_devices[i]; struct i2c_adapter *i2c; int gpio; + bool dvoinit; /* Allow the I2C driver info to specify the GPIO to be used in * special cases, but otherwise default to what's defined @@ -468,7 +469,17 @@ void intel_dvo_init(struct drm_device *d i2c = intel_gmbus_get_adapter(dev_priv, gpio); intel_dvo->dev = *dvo; - if (!dvo->dev_ops->init(&intel_dvo->dev, i2c)) + + /* GMBUS NAK handling seems to be unstable, hence let the + * transmitter detection run in bit banging mode for now. + */ + intel_gmbus_force_bit(i2c, true); + + dvoinit = dvo->dev_ops->init(&intel_dvo->dev, i2c); + + intel_gmbus_force_bit(i2c, false); + + if (!dvoinit) continue; intel_encoder->type = INTEL_OUTPUT_DVO;