144d0b80e5ff741d502a6ccc8685a18bda1ac9da4Joe Perches#define pr_fmt(fmt) KBUILD_MODNAME ": " fmt 244d0b80e5ff741d502a6ccc8685a18bda1ac9da4Joe Perches 31da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds#include <media/saa7146_vv.h> 41da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds 51da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvaldsstatic u32 saa7146_i2c_func(struct i2c_adapter *adapter) 61da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds{ 744d0b80e5ff741d502a6ccc8685a18bda1ac9da4Joe Perches /* DEB_I2C("'%s'\n", adapter->name); */ 81da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds 91da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds return I2C_FUNC_I2C 101da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds | I2C_FUNC_SMBUS_QUICK 111da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds | I2C_FUNC_SMBUS_READ_BYTE | I2C_FUNC_SMBUS_WRITE_BYTE 121da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds | I2C_FUNC_SMBUS_READ_BYTE_DATA | I2C_FUNC_SMBUS_WRITE_BYTE_DATA; 131da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds} 141da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds 151da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds/* this function returns the status-register of our i2c-device */ 161da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvaldsstatic inline u32 saa7146_i2c_status(struct saa7146_dev *dev) 171da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds{ 181da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds u32 iicsta = saa7146_read(dev, I2C_STATUS); 1944d0b80e5ff741d502a6ccc8685a18bda1ac9da4Joe Perches /* DEB_I2C("status: 0x%08x\n", iicsta); */ 201da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds return iicsta; 211da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds} 221da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds 231da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds/* this function runs through the i2c-messages and prepares the data to be 241da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds sent through the saa7146. have a look at the specifications p. 122 ff 251da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds to understand this. it returns the number of u32s to send, or -1 261da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds in case of an error. */ 27a36ef6b1e09d06d4f1ac769eee4bd7e6cf3e0faeAl Virostatic int saa7146_i2c_msg_prepare(const struct i2c_msg *m, int num, __le32 *op) 281da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds{ 291da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds int h1, h2; 301da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds int i, j, addr; 311da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds int mem = 0, op_count = 0; 321da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds 331da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds /* first determine size of needed memory */ 341da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds for(i = 0; i < num; i++) { 351da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds mem += m[i].len + 1; 361da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds } 371da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds 381da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds /* worst case: we need one u32 for three bytes to be send 391da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds plus one extra byte to address the device */ 401da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds mem = 1 + ((mem-1) / 3); 411da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds 4244d0b80e5ff741d502a6ccc8685a18bda1ac9da4Joe Perches /* we assume that op points to a memory of at least 4344d0b80e5ff741d502a6ccc8685a18bda1ac9da4Joe Perches * SAA7146_I2C_MEM bytes size. if we exceed this limit... 4444d0b80e5ff741d502a6ccc8685a18bda1ac9da4Joe Perches */ 4544d0b80e5ff741d502a6ccc8685a18bda1ac9da4Joe Perches if ((4 * mem) > SAA7146_I2C_MEM) { 4644d0b80e5ff741d502a6ccc8685a18bda1ac9da4Joe Perches /* DEB_I2C("cannot prepare i2c-message\n"); */ 471da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds return -ENOMEM; 481da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds } 491da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds 501da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds /* be careful: clear out the i2c-mem first */ 51a36ef6b1e09d06d4f1ac769eee4bd7e6cf3e0faeAl Viro memset(op,0,sizeof(__le32)*mem); 521da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds 531da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds /* loop through all messages */ 541da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds for(i = 0; i < num; i++) { 551da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds 561da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds /* insert the address of the i2c-slave. 571da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds note: we get 7 bit i2c-addresses, 581da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds so we have to perform a translation */ 591da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds addr = (m[i].addr*2) + ( (0 != (m[i].flags & I2C_M_RD)) ? 1 : 0); 601da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds h1 = op_count/3; h2 = op_count%3; 61a36ef6b1e09d06d4f1ac769eee4bd7e6cf3e0faeAl Viro op[h1] |= cpu_to_le32( (u8)addr << ((3-h2)*8)); 62a36ef6b1e09d06d4f1ac769eee4bd7e6cf3e0faeAl Viro op[h1] |= cpu_to_le32(SAA7146_I2C_START << ((3-h2)*2)); 631da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds op_count++; 641da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds 651da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds /* loop through all bytes of message i */ 661da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds for(j = 0; j < m[i].len; j++) { 671da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds /* insert the data bytes */ 681da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds h1 = op_count/3; h2 = op_count%3; 69a36ef6b1e09d06d4f1ac769eee4bd7e6cf3e0faeAl Viro op[h1] |= cpu_to_le32( (u32)((u8)m[i].buf[j]) << ((3-h2)*8)); 70a36ef6b1e09d06d4f1ac769eee4bd7e6cf3e0faeAl Viro op[h1] |= cpu_to_le32( SAA7146_I2C_CONT << ((3-h2)*2)); 711da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds op_count++; 721da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds } 731da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds 741da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds } 751da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds 761da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds /* have a look at the last byte inserted: 771da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds if it was: ...CONT change it to ...STOP */ 781da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds h1 = (op_count-1)/3; h2 = (op_count-1)%3; 79a36ef6b1e09d06d4f1ac769eee4bd7e6cf3e0faeAl Viro if ( SAA7146_I2C_CONT == (0x3 & (le32_to_cpu(op[h1]) >> ((3-h2)*2))) ) { 80a36ef6b1e09d06d4f1ac769eee4bd7e6cf3e0faeAl Viro op[h1] &= ~cpu_to_le32(0x2 << ((3-h2)*2)); 81a36ef6b1e09d06d4f1ac769eee4bd7e6cf3e0faeAl Viro op[h1] |= cpu_to_le32(SAA7146_I2C_STOP << ((3-h2)*2)); 821da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds } 831da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds 841da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds /* return the number of u32s to send */ 851da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds return mem; 861da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds} 871da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds 881da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds/* this functions loops through all i2c-messages. normally, it should determine 891da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds which bytes were read through the adapter and write them back to the corresponding 901da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds i2c-message. but instead, we simply write back all bytes. 911da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds fixme: this could be improved. */ 92a36ef6b1e09d06d4f1ac769eee4bd7e6cf3e0faeAl Virostatic int saa7146_i2c_msg_cleanup(const struct i2c_msg *m, int num, __le32 *op) 931da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds{ 941da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds int i, j; 951da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds int op_count = 0; 961da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds 971da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds /* loop through all messages */ 981da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds for(i = 0; i < num; i++) { 991da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds 1001da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds op_count++; 1011da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds 102af901ca181d92aac3a7dc265144a9081a86d8f39André Goddard Rosa /* loop through all bytes of message i */ 1031da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds for(j = 0; j < m[i].len; j++) { 1041da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds /* write back all bytes that could have been read */ 105a36ef6b1e09d06d4f1ac769eee4bd7e6cf3e0faeAl Viro m[i].buf[j] = (le32_to_cpu(op[op_count/3]) >> ((3-(op_count%3))*8)); 1061da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds op_count++; 1071da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds } 1081da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds } 1091da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds 1101da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds return 0; 1111da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds} 1121da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds 1131da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds/* this functions resets the i2c-device and returns 0 if everything was fine, otherwise -1 */ 1141da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvaldsstatic int saa7146_i2c_reset(struct saa7146_dev *dev) 1151da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds{ 1161da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds /* get current status */ 1171da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds u32 status = saa7146_i2c_status(dev); 1181da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds 1191da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds /* clear registers for sure */ 1201da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds saa7146_write(dev, I2C_STATUS, dev->i2c_bitrate); 1211da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds saa7146_write(dev, I2C_TRANSFER, 0); 1221da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds 1231da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds /* check if any operation is still in progress */ 1241da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds if ( 0 != ( status & SAA7146_I2C_BUSY) ) { 1251da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds 1261da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds /* yes, kill ongoing operation */ 12744d0b80e5ff741d502a6ccc8685a18bda1ac9da4Joe Perches DEB_I2C("busy_state detected\n"); 1281da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds 1291da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds /* set "ABORT-OPERATION"-bit (bit 7)*/ 1301da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds saa7146_write(dev, I2C_STATUS, (dev->i2c_bitrate | MASK_07)); 1311da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds saa7146_write(dev, MC2, (MASK_00 | MASK_16)); 1321da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds msleep(SAA7146_I2C_DELAY); 1331da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds 1341da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds /* clear all error-bits pending; this is needed because p.123, note 1 */ 1351da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds saa7146_write(dev, I2C_STATUS, dev->i2c_bitrate); 1361da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds saa7146_write(dev, MC2, (MASK_00 | MASK_16)); 1371da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds msleep(SAA7146_I2C_DELAY); 1381da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds } 1391da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds 1401da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds /* check if any error is (still) present. (this can be necessary because p.123, note 1) */ 1411da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds status = saa7146_i2c_status(dev); 1421da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds 1431da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds if ( dev->i2c_bitrate != status ) { 1441da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds 14544d0b80e5ff741d502a6ccc8685a18bda1ac9da4Joe Perches DEB_I2C("error_state detected. status:0x%08x\n", status); 1461da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds 1471da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds /* Repeat the abort operation. This seems to be necessary 1481da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds after serious protocol errors caused by e.g. the SAA7740 */ 1491da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds saa7146_write(dev, I2C_STATUS, (dev->i2c_bitrate | MASK_07)); 1501da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds saa7146_write(dev, MC2, (MASK_00 | MASK_16)); 1511da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds msleep(SAA7146_I2C_DELAY); 1521da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds 1531da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds /* clear all error-bits pending */ 1541da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds saa7146_write(dev, I2C_STATUS, dev->i2c_bitrate); 1551da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds saa7146_write(dev, MC2, (MASK_00 | MASK_16)); 1561da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds msleep(SAA7146_I2C_DELAY); 1571da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds 1581da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds /* the data sheet says it might be necessary to clear the status 1591da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds twice after an abort */ 1601da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds saa7146_write(dev, I2C_STATUS, dev->i2c_bitrate); 1611da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds saa7146_write(dev, MC2, (MASK_00 | MASK_16)); 1621da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds msleep(SAA7146_I2C_DELAY); 1631da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds } 1641da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds 16525985edcedea6396277003854657b5f3cb31a628Lucas De Marchi /* if any error is still present, a fatal error has occurred ... */ 1661da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds status = saa7146_i2c_status(dev); 1671da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds if ( dev->i2c_bitrate != status ) { 16844d0b80e5ff741d502a6ccc8685a18bda1ac9da4Joe Perches DEB_I2C("fatal error. status:0x%08x\n", status); 1691da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds return -1; 1701da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds } 1711da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds 1721da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds return 0; 1731da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds} 1741da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds 1751da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds/* this functions writes out the data-byte 'dword' to the i2c-device. 1761da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds it returns 0 if ok, -1 if the transfer failed, -2 if the transfer 1771da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds failed badly (e.g. address error) */ 178a36ef6b1e09d06d4f1ac769eee4bd7e6cf3e0faeAl Virostatic int saa7146_i2c_writeout(struct saa7146_dev *dev, __le32 *dword, int short_delay) 1791da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds{ 1801da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds u32 status = 0, mc2 = 0; 1811da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds int trial = 0; 1821da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds unsigned long timeout; 1831da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds 1841da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds /* write out i2c-command */ 18544d0b80e5ff741d502a6ccc8685a18bda1ac9da4Joe Perches DEB_I2C("before: 0x%08x (status: 0x%08x), %d\n", 18644d0b80e5ff741d502a6ccc8685a18bda1ac9da4Joe Perches *dword, saa7146_read(dev, I2C_STATUS), dev->i2c_op); 1871da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds 1881da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds if( 0 != (SAA7146_USE_I2C_IRQ & dev->ext->flags)) { 1891da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds 1901da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds saa7146_write(dev, I2C_STATUS, dev->i2c_bitrate); 191a36ef6b1e09d06d4f1ac769eee4bd7e6cf3e0faeAl Viro saa7146_write(dev, I2C_TRANSFER, le32_to_cpu(*dword)); 1921da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds 1931da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds dev->i2c_op = 1; 19435e55255bbe1775c3cdb5d9cff494d72d5a49bf3Hartmut Birr SAA7146_ISR_CLEAR(dev, MASK_16|MASK_17); 1951da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds SAA7146_IER_ENABLE(dev, MASK_16|MASK_17); 1961da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds saa7146_write(dev, MC2, (MASK_00 | MASK_16)); 1971da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds 19835e55255bbe1775c3cdb5d9cff494d72d5a49bf3Hartmut Birr timeout = HZ/100 + 1; /* 10ms */ 19935e55255bbe1775c3cdb5d9cff494d72d5a49bf3Hartmut Birr timeout = wait_event_interruptible_timeout(dev->i2c_wq, dev->i2c_op == 0, timeout); 20035e55255bbe1775c3cdb5d9cff494d72d5a49bf3Hartmut Birr if (timeout == -ERESTARTSYS || dev->i2c_op) { 20135e55255bbe1775c3cdb5d9cff494d72d5a49bf3Hartmut Birr SAA7146_IER_DISABLE(dev, MASK_16|MASK_17); 20235e55255bbe1775c3cdb5d9cff494d72d5a49bf3Hartmut Birr SAA7146_ISR_CLEAR(dev, MASK_16|MASK_17); 20335e55255bbe1775c3cdb5d9cff494d72d5a49bf3Hartmut Birr if (timeout == -ERESTARTSYS) 20435e55255bbe1775c3cdb5d9cff494d72d5a49bf3Hartmut Birr /* a signal arrived */ 20535e55255bbe1775c3cdb5d9cff494d72d5a49bf3Hartmut Birr return -ERESTARTSYS; 20635e55255bbe1775c3cdb5d9cff494d72d5a49bf3Hartmut Birr 20744d0b80e5ff741d502a6ccc8685a18bda1ac9da4Joe Perches pr_warn("%s %s [irq]: timed out waiting for end of xfer\n", 208536a0b119527c8af8e3a70b18f7640a21039a0a7Harvey Harrison dev->name, __func__); 20935e55255bbe1775c3cdb5d9cff494d72d5a49bf3Hartmut Birr return -EIO; 2101da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds } 2111da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds status = saa7146_read(dev, I2C_STATUS); 2121da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds } else { 2131da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds saa7146_write(dev, I2C_STATUS, dev->i2c_bitrate); 214a36ef6b1e09d06d4f1ac769eee4bd7e6cf3e0faeAl Viro saa7146_write(dev, I2C_TRANSFER, le32_to_cpu(*dword)); 2151da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds saa7146_write(dev, MC2, (MASK_00 | MASK_16)); 2161da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds 2171da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds /* do not poll for i2c-status before upload is complete */ 2181da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds timeout = jiffies + HZ/100 + 1; /* 10ms */ 2191da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds while(1) { 2201da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds mc2 = (saa7146_read(dev, MC2) & 0x1); 2211da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds if( 0 != mc2 ) { 2221da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds break; 2231da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds } 2241da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds if (time_after(jiffies,timeout)) { 22544d0b80e5ff741d502a6ccc8685a18bda1ac9da4Joe Perches pr_warn("%s %s: timed out waiting for MC2\n", 226536a0b119527c8af8e3a70b18f7640a21039a0a7Harvey Harrison dev->name, __func__); 2271da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds return -EIO; 2281da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds } 2291da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds } 2301da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds /* wait until we get a transfer done or error */ 2311da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds timeout = jiffies + HZ/100 + 1; /* 10ms */ 2329bb6e2593ad4cb94944f547154baee64b4734598Oliver Endriss /* first read usually delivers bogus results... */ 2339bb6e2593ad4cb94944f547154baee64b4734598Oliver Endriss saa7146_i2c_status(dev); 2341da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds while(1) { 2351da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds status = saa7146_i2c_status(dev); 2361da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds if ((status & 0x3) != 1) 2371da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds break; 2381da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds if (time_after(jiffies,timeout)) { 2391da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds /* this is normal when probing the bus 2401da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds * (no answer from nonexisistant device...) 2411da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds */ 24244d0b80e5ff741d502a6ccc8685a18bda1ac9da4Joe Perches pr_warn("%s %s [poll]: timed out waiting for end of xfer\n", 243536a0b119527c8af8e3a70b18f7640a21039a0a7Harvey Harrison dev->name, __func__); 2441da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds return -EIO; 2451da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds } 2469bb6e2593ad4cb94944f547154baee64b4734598Oliver Endriss if (++trial < 50 && short_delay) 2471da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds udelay(10); 2481da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds else 2499bb6e2593ad4cb94944f547154baee64b4734598Oliver Endriss msleep(1); 2501da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds } 2511da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds } 2521da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds 2531da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds /* give a detailed status report */ 254276e49a01a7e6c4a7bfb78618cf2f5befbf9f5deOliver Endriss if ( 0 != (status & (SAA7146_I2C_SPERR | SAA7146_I2C_APERR | 255276e49a01a7e6c4a7bfb78618cf2f5befbf9f5deOliver Endriss SAA7146_I2C_DTERR | SAA7146_I2C_DRERR | 256276e49a01a7e6c4a7bfb78618cf2f5befbf9f5deOliver Endriss SAA7146_I2C_AL | SAA7146_I2C_ERR | 257276e49a01a7e6c4a7bfb78618cf2f5befbf9f5deOliver Endriss SAA7146_I2C_BUSY)) ) { 258276e49a01a7e6c4a7bfb78618cf2f5befbf9f5deOliver Endriss 259276e49a01a7e6c4a7bfb78618cf2f5befbf9f5deOliver Endriss if ( 0 == (status & SAA7146_I2C_ERR) || 260276e49a01a7e6c4a7bfb78618cf2f5befbf9f5deOliver Endriss 0 == (status & SAA7146_I2C_BUSY) ) { 261276e49a01a7e6c4a7bfb78618cf2f5befbf9f5deOliver Endriss /* it may take some time until ERR goes high - ignore */ 26244d0b80e5ff741d502a6ccc8685a18bda1ac9da4Joe Perches DEB_I2C("unexpected i2c status %04x\n", status); 263276e49a01a7e6c4a7bfb78618cf2f5befbf9f5deOliver Endriss } 2641da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds if( 0 != (status & SAA7146_I2C_SPERR) ) { 26544d0b80e5ff741d502a6ccc8685a18bda1ac9da4Joe Perches DEB_I2C("error due to invalid start/stop condition\n"); 2661da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds } 2671da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds if( 0 != (status & SAA7146_I2C_DTERR) ) { 26844d0b80e5ff741d502a6ccc8685a18bda1ac9da4Joe Perches DEB_I2C("error in data transmission\n"); 2691da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds } 2701da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds if( 0 != (status & SAA7146_I2C_DRERR) ) { 27144d0b80e5ff741d502a6ccc8685a18bda1ac9da4Joe Perches DEB_I2C("error when receiving data\n"); 2721da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds } 2731da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds if( 0 != (status & SAA7146_I2C_AL) ) { 27444d0b80e5ff741d502a6ccc8685a18bda1ac9da4Joe Perches DEB_I2C("error because arbitration lost\n"); 2751da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds } 2761da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds 2771da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds /* we handle address-errors here */ 2781da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds if( 0 != (status & SAA7146_I2C_APERR) ) { 27944d0b80e5ff741d502a6ccc8685a18bda1ac9da4Joe Perches DEB_I2C("error in address phase\n"); 2801da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds return -EREMOTEIO; 2811da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds } 2821da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds 2831da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds return -EIO; 2841da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds } 2851da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds 2861da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds /* read back data, just in case we were reading ... */ 287a36ef6b1e09d06d4f1ac769eee4bd7e6cf3e0faeAl Viro *dword = cpu_to_le32(saa7146_read(dev, I2C_TRANSFER)); 2881da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds 28944d0b80e5ff741d502a6ccc8685a18bda1ac9da4Joe Perches DEB_I2C("after: 0x%08x\n", *dword); 2901da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds return 0; 2911da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds} 2921da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds 29336c15f8ee41fbc3d8eaf88bba95be3d50268d5d2Oliver Endrissstatic int saa7146_i2c_transfer(struct saa7146_dev *dev, const struct i2c_msg *msgs, int num, int retries) 2941da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds{ 2951da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds int i = 0, count = 0; 296a36ef6b1e09d06d4f1ac769eee4bd7e6cf3e0faeAl Viro __le32 *buffer = dev->d_i2c.cpu_addr; 2971da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds int err = 0; 298afd1a0c9ac281eed3b22b293ccd92af7b0d60889Mauro Carvalho Chehab int short_delay = 0; 2991da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds 3003593cab5d62c4c7abced1076710f9bc2d8847433Ingo Molnar if (mutex_lock_interruptible(&dev->i2c_lock)) 3011da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds return -ERESTARTSYS; 3021da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds 3031da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds for(i=0;i<num;i++) { 30444d0b80e5ff741d502a6ccc8685a18bda1ac9da4Joe Perches DEB_I2C("msg:%d/%d\n", i+1, num); 3051da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds } 3061da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds 3071da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds /* prepare the message(s), get number of u32s to transfer */ 3081da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds count = saa7146_i2c_msg_prepare(msgs, num, buffer); 3091da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds if ( 0 > count ) { 3101da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds err = -1; 3111da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds goto out; 3121da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds } 3131da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds 3141da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds if ( count > 3 || 0 != (SAA7146_I2C_SHORT_DELAY & dev->ext->flags) ) 3151da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds short_delay = 1; 3161da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds 3171da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds do { 3181da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds /* reset the i2c-device if necessary */ 3191da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds err = saa7146_i2c_reset(dev); 3201da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds if ( 0 > err ) { 32144d0b80e5ff741d502a6ccc8685a18bda1ac9da4Joe Perches DEB_I2C("could not reset i2c-device\n"); 3221da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds goto out; 3231da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds } 3241da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds 3251da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds /* write out the u32s one after another */ 3261da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds for(i = 0; i < count; i++) { 3271da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds err = saa7146_i2c_writeout(dev, &buffer[i], short_delay); 3281da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds if ( 0 != err) { 3291da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds /* this one is unsatisfying: some i2c slaves on some 3301da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds dvb cards don't acknowledge correctly, so the saa7146 33125985edcedea6396277003854657b5f3cb31a628Lucas De Marchi thinks that an address error occurred. in that case, the 3321da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds transaction should be retrying, even if an address error 33325985edcedea6396277003854657b5f3cb31a628Lucas De Marchi occurred. analog saa7146 based cards extensively rely on 3341da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds i2c address probing, however, and address errors indicate that a 3351da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds device is really *not* there. retrying in that case 3361da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds increases the time the device needs to probe greatly, so 337632fe9fe440249642845675d97436c667cbbd21eOliver Endriss it should be avoided. So we bail out in irq mode after an 338632fe9fe440249642845675d97436c667cbbd21eOliver Endriss address error and trust the saa7146 address error detection. */ 339632fe9fe440249642845675d97436c667cbbd21eOliver Endriss if (-EREMOTEIO == err && 0 != (SAA7146_USE_I2C_IRQ & dev->ext->flags)) 340632fe9fe440249642845675d97436c667cbbd21eOliver Endriss goto out; 34144d0b80e5ff741d502a6ccc8685a18bda1ac9da4Joe Perches DEB_I2C("error while sending message(s). starting again\n"); 3421da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds break; 3431da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds } 3441da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds } 3451da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds if( 0 == err ) { 3461da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds err = num; 3471da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds break; 3481da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds } 3491da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds 350afd1a0c9ac281eed3b22b293ccd92af7b0d60889Mauro Carvalho Chehab /* delay a bit before retrying */ 351afd1a0c9ac281eed3b22b293ccd92af7b0d60889Mauro Carvalho Chehab msleep(10); 3521da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds 3531da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds } while (err != num && retries--); 3541da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds 355632fe9fe440249642845675d97436c667cbbd21eOliver Endriss /* quit if any error occurred */ 356632fe9fe440249642845675d97436c667cbbd21eOliver Endriss if (err != num) 357afd1a0c9ac281eed3b22b293ccd92af7b0d60889Mauro Carvalho Chehab goto out; 3581da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds 3591da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds /* if any things had to be read, get the results */ 3601da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds if ( 0 != saa7146_i2c_msg_cleanup(msgs, num, buffer)) { 36144d0b80e5ff741d502a6ccc8685a18bda1ac9da4Joe Perches DEB_I2C("could not cleanup i2c-message\n"); 3621da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds err = -1; 3631da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds goto out; 3641da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds } 3651da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds 3661da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds /* return the number of delivered messages */ 36744d0b80e5ff741d502a6ccc8685a18bda1ac9da4Joe Perches DEB_I2C("transmission successful. (msg:%d)\n", err); 3681da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvaldsout: 3691da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds /* another bug in revision 0: the i2c-registers get uploaded randomly by other 37025985edcedea6396277003854657b5f3cb31a628Lucas De Marchi uploads, so we better clear them out before continuing */ 3711da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds if( 0 == dev->revision ) { 372a36ef6b1e09d06d4f1ac769eee4bd7e6cf3e0faeAl Viro __le32 zero = 0; 3731da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds saa7146_i2c_reset(dev); 3741da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds if( 0 != saa7146_i2c_writeout(dev, &zero, short_delay)) { 37544d0b80e5ff741d502a6ccc8685a18bda1ac9da4Joe Perches pr_info("revision 0 error. this should never happen\n"); 3761da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds } 3771da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds } 3781da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds 3793593cab5d62c4c7abced1076710f9bc2d8847433Ingo Molnar mutex_unlock(&dev->i2c_lock); 3801da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds return err; 3811da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds} 3821da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds 3831da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds/* utility functions */ 3841da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvaldsstatic int saa7146_i2c_xfer(struct i2c_adapter* adapter, struct i2c_msg *msg, int num) 3851da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds{ 38645d809431daaa3ab01f877388d09676d05b469beHans Verkuil struct v4l2_device *v4l2_dev = i2c_get_adapdata(adapter); 38745d809431daaa3ab01f877388d09676d05b469beHans Verkuil struct saa7146_dev *dev = to_saa7146_dev(v4l2_dev); 3881da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds 3891da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds /* use helper function to transfer data */ 3901da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds return saa7146_i2c_transfer(dev, msg, num, adapter->retries); 3911da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds} 3921da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds 3931da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds 3941da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds/*****************************************************************************/ 3951da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds/* i2c-adapter helper functions */ 3961da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds 3971da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds/* exported algorithm data */ 3981da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvaldsstatic struct i2c_algorithm saa7146_algo = { 3991da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds .master_xfer = saa7146_i2c_xfer, 4001da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds .functionality = saa7146_i2c_func, 4011da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds}; 4021da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds 4031da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvaldsint saa7146_i2c_adapter_prepare(struct saa7146_dev *dev, struct i2c_adapter *i2c_adapter, u32 bitrate) 4041da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds{ 40544d0b80e5ff741d502a6ccc8685a18bda1ac9da4Joe Perches DEB_EE("bitrate: 0x%08x\n", bitrate); 4061da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds 4071da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds /* enable i2c-port pins */ 4081da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds saa7146_write(dev, MC1, (MASK_08 | MASK_24)); 4091da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds 4101da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds dev->i2c_bitrate = bitrate; 4111da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds saa7146_i2c_reset(dev); 4121da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds 413d30e21ddcdc948ecedfb46a0ed021d57f310a6f3Hans Verkuil if (i2c_adapter) { 41445d809431daaa3ab01f877388d09676d05b469beHans Verkuil i2c_set_adapdata(i2c_adapter, &dev->v4l2_dev); 4151ac2854cbc637de7e958cfa8d153ccf9e6668ddaPhilipp Matthias Hahn i2c_adapter->dev.parent = &dev->pci->dev; 4161da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds i2c_adapter->algo = &saa7146_algo; 4171da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds i2c_adapter->algo_data = NULL; 4181da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds i2c_adapter->timeout = SAA7146_I2C_TIMEOUT; 4191da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds i2c_adapter->retries = SAA7146_I2C_RETRIES; 4201da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds } 4211da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds 4221da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds return 0; 4231da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds} 424