dvbsky_m88rs6000: Make i2c transactions in tuner_read/writereg() atomic

Frequent failures have been observed when accessing tuner registers on
a busy i2c bus:

[   44.033334] comcerto_i2c comcerto_i2c.0: comcerto_i2c_tx: unexpected
               state (0x20) on address phase, aborting
[   44.043221] slowirq 62 (9668us)
[   44.046515] comcerto_i2c comcerto_i2c.0: comcerto_i2c_master_xfer:
               transfer failed on message #0 (addr=0x21, flags=0x0, len=2)
[   44.058413] m88rs6000_tuner_writereg: writereg error(err == -5,
               reg == 0x05, value == 0x00)

Before reading/writing a tuner register the 2-wire bus repeater needs
to be enabled. The repeater is switched off automatically after a
configurable number of i2c transactions. The driver uses i2c_transfer()
to enable the repeater and calls i2c_transfer() again to access the
tuner register. i2c_transfer() acquires the i2c bus lock and releases it
before returning. This gives other i2c slaves on the same bus the
opportunity to grab the i2c bus after the repeater has been enabled and
perform their transactions. When the m88rs6000 regains control over the
bus the repeater has been switched off again, which causes the above
failure.

To avoid this situation the i2c bus lock must not be released after
enabling the repeater but held until the access to the tuner register is
finished. Use the unlocked __i2c_transfer() instead of i2c_transfer()
and acquire/release the bus lock in the m88rs6000 driver.

Change-Id: I53a1fe63c4d5af2b7e8c2484809d143745682580
1 file changed