Linux kernel mirror (for testing) git.kernel.org/pub/scm/linux/kernel/git/torvalds/linux.git
kernel os linux

[media] mt2060: add param to split long i2c writes

Add configuration parameter to split long i2c writes as some I2C
adapters cannot write 10 bytes used as a one go.

Signed-off-by: Antti Palosaari <crope@iki.fi>
Signed-off-by: Mauro Carvalho Chehab <mchehab@s-opensource.com>

authored by

Antti Palosaari and committed by
Mauro Carvalho Chehab
433c4864 59e8b7aa

+21 -4
+17 -4
drivers/media/tuners/mt2060.c
··· 67 67 // Writes a set of consecutive registers 68 68 static int mt2060_writeregs(struct mt2060_priv *priv,u8 *buf, u8 len) 69 69 { 70 + int rem, val_len; 71 + u8 xfer_buf[16]; 70 72 struct i2c_msg msg = { 71 - .addr = priv->cfg->i2c_address, .flags = 0, .buf = buf, .len = len 73 + .addr = priv->cfg->i2c_address, .flags = 0, .buf = xfer_buf 72 74 }; 73 - if (i2c_transfer(priv->i2c, &msg, 1) != 1) { 74 - printk(KERN_WARNING "mt2060 I2C write failed (len=%i)\n",(int)len); 75 - return -EREMOTEIO; 75 + 76 + for (rem = len - 1; rem > 0; rem -= priv->i2c_max_regs) { 77 + val_len = min_t(int, rem, priv->i2c_max_regs); 78 + msg.len = 1 + val_len; 79 + xfer_buf[0] = buf[0] + len - 1 - rem; 80 + memcpy(&xfer_buf[1], &buf[1 + len - 1 - rem], val_len); 81 + 82 + if (i2c_transfer(priv->i2c, &msg, 1) != 1) { 83 + printk(KERN_WARNING "mt2060 I2C write failed (len=%i)\n", val_len); 84 + return -EREMOTEIO; 85 + } 76 86 } 87 + 77 88 return 0; 78 89 } 79 90 ··· 376 365 priv->cfg = cfg; 377 366 priv->i2c = i2c; 378 367 priv->if1_freq = if1; 368 + priv->i2c_max_regs = ~0; 379 369 380 370 if (fe->ops.i2c_gate_ctrl) 381 371 fe->ops.i2c_gate_ctrl(fe, 1); /* open i2c_gate */ ··· 434 422 dev->i2c = client->adapter; 435 423 dev->if1_freq = pdata->if1 ? pdata->if1 : 1220; 436 424 dev->client = client; 425 + dev->i2c_max_regs = pdata->i2c_write_max ? pdata->i2c_write_max - 1 : ~0; 437 426 438 427 ret = mt2060_readreg(dev, REG_PART_REV, &chip_id); 439 428 if (ret) {
+3
drivers/media/tuners/mt2060.h
··· 30 30 * struct mt2060_platform_data - Platform data for the mt2060 driver 31 31 * @clock_out: Clock output setting. 0 = off, 1 = CLK/4, 2 = CLK/2, 3 = CLK/1. 32 32 * @if1: First IF used [MHz]. 0 defaults to 1220. 33 + * @i2c_write_max: Maximum number of bytes I2C adapter can write at once. 34 + * 0 defaults to maximum. 33 35 * @dvb_frontend: DVB frontend. 34 36 */ 35 37 36 38 struct mt2060_platform_data { 37 39 u8 clock_out; 38 40 u16 if1; 41 + unsigned int i2c_write_max:5; 39 42 struct dvb_frontend *dvb_frontend; 40 43 }; 41 44
+1
drivers/media/tuners/mt2060_priv.h
··· 94 94 struct i2c_client *client; 95 95 struct mt2060_config config; 96 96 97 + u8 i2c_max_regs; 97 98 u32 frequency; 98 99 u16 if1_freq; 99 100 u8 fmfreq;