diff options
Diffstat (limited to 'drivers/i2c')
38 files changed, 1496 insertions, 783 deletions
| diff --git a/drivers/i2c/algos/i2c-algo-bit.c b/drivers/i2c/algos/i2c-algo-bit.c index d420cc5f563..e25e13980af 100644 --- a/drivers/i2c/algos/i2c-algo-bit.c +++ b/drivers/i2c/algos/i2c-algo-bit.c @@ -104,7 +104,7 @@ static int sclhi(struct i2c_algo_bit_data *adap)  		 * chips may hold it low ("clock stretching") while they  		 * are processing data internally.  		 */ -		if (time_after_eq(jiffies, start + adap->timeout)) +		if (time_after(jiffies, start + adap->timeout))  			return -ETIMEDOUT;  		cond_resched();  	} diff --git a/drivers/i2c/algos/i2c-algo-pca.c b/drivers/i2c/algos/i2c-algo-pca.c index 6318f7ddc1d..78d42aae008 100644 --- a/drivers/i2c/algos/i2c-algo-pca.c +++ b/drivers/i2c/algos/i2c-algo-pca.c @@ -287,10 +287,21 @@ static int pca_xfer(struct i2c_adapter *i2c_adap,  		case 0x30: /* Data byte in I2CDAT has been transmitted; NOT ACK has been received */  			DEB2("NOT ACK received after data byte\n"); +			pca_stop(adap);  			goto out;  		case 0x38: /* Arbitration lost during SLA+W, SLA+R or data bytes */  			DEB2("Arbitration lost\n"); +			/* +			 * The PCA9564 data sheet (2006-09-01) says "A +			 * START condition will be transmitted when the +			 * bus becomes free (STOP or SCL and SDA high)" +			 * when the STA bit is set (p. 11). +			 * +			 * In case this won't work, try pca_reset() +			 * instead. +			 */ +			pca_start(adap);  			goto out;  		case 0x58: /* Data byte has been received; NOT ACK has been returned */ diff --git a/drivers/i2c/busses/Kconfig b/drivers/i2c/busses/Kconfig index a48c8aee021..3c259ee7ddd 100644 --- a/drivers/i2c/busses/Kconfig +++ b/drivers/i2c/busses/Kconfig @@ -211,7 +211,7 @@ config I2C_VIA  	  will be called i2c-via.  config I2C_VIAPRO -	tristate "VIA VT82C596/82C686/82xx and CX700/VX800/VX820" +	tristate "VIA VT82C596/82C686/82xx and CX700/VX8xx"  	depends on PCI  	help  	  If you say yes to this option, support will be included for the VIA @@ -225,8 +225,8 @@ config I2C_VIAPRO  	    VT8237R/A/S  	    VT8251  	    CX700 -	    VX800 -	    VX820 +	    VX800/VX820 +	    VX855/VX875  	  This driver can also be built as a module.  If so, the module  	  will be called i2c-viapro. @@ -298,7 +298,7 @@ config I2C_BLACKFIN_TWI  config I2C_BLACKFIN_TWI_CLK_KHZ  	int "Blackfin TWI I2C clock (kHz)"  	depends on I2C_BLACKFIN_TWI -	range 10 400 +	range 21 400  	default 50  	help  	  The unit of the TWI clock is kHz. @@ -467,7 +467,7 @@ config I2C_PXA_SLAVE  config I2C_S3C2410  	tristate "S3C2410 I2C Driver" -	depends on ARCH_S3C2410 +	depends on ARCH_S3C2410 || ARCH_S3C64XX  	help  	  Say Y here to include support for I2C controller in the  	  Samsung S3C2410 based System-on-Chip devices. @@ -513,6 +513,19 @@ config I2C_SIMTEC  	  This driver can also be built as a module. If so, the module  	  will be called i2c-simtec. +config I2C_STU300 +	tristate "ST Microelectronics DDC I2C interface" +	depends on MACH_U300 +	default y if MACH_U300 +	help +	  If you say yes to this option, support will be included for the +	  I2C interface from ST Microelectronics simply called "DDC I2C" +	  supporting both I2C and DDC, used in e.g. the U300 series +	  mobile platforms. + +	  This driver can also be built as a module. If so, the module +	  will be called i2c-stu300. +  config I2C_VERSATILE  	tristate "ARM Versatile/Realview I2C bus support"  	depends on ARCH_VERSATILE || ARCH_REALVIEW diff --git a/drivers/i2c/busses/Makefile b/drivers/i2c/busses/Makefile index 776acb6403a..edeabf00310 100644 --- a/drivers/i2c/busses/Makefile +++ b/drivers/i2c/busses/Makefile @@ -48,6 +48,7 @@ obj-$(CONFIG_I2C_S6000)		+= i2c-s6000.o  obj-$(CONFIG_I2C_SH7760)	+= i2c-sh7760.o  obj-$(CONFIG_I2C_SH_MOBILE)	+= i2c-sh_mobile.o  obj-$(CONFIG_I2C_SIMTEC)	+= i2c-simtec.o +obj-$(CONFIG_I2C_STU300)	+= i2c-stu300.o  obj-$(CONFIG_I2C_VERSATILE)	+= i2c-versatile.o  # External I2C/SMBus adapter drivers diff --git a/drivers/i2c/busses/i2c-ali1535.c b/drivers/i2c/busses/i2c-ali1535.c index 981e080b32a..d108450df06 100644 --- a/drivers/i2c/busses/i2c-ali1535.c +++ b/drivers/i2c/busses/i2c-ali1535.c @@ -284,7 +284,7 @@ static int ali1535_transaction(struct i2c_adapter *adap)  		 && (timeout++ < MAX_TIMEOUT));  	/* If the SMBus is still busy, we give up */ -	if (timeout >= MAX_TIMEOUT) { +	if (timeout > MAX_TIMEOUT) {  		result = -ETIMEDOUT;  		dev_err(&adap->dev, "SMBus Timeout!\n");  	} diff --git a/drivers/i2c/busses/i2c-ali15x3.c b/drivers/i2c/busses/i2c-ali15x3.c index 39066dee46e..d627fceb790 100644 --- a/drivers/i2c/busses/i2c-ali15x3.c +++ b/drivers/i2c/busses/i2c-ali15x3.c @@ -306,7 +306,7 @@ static int ali15x3_transaction(struct i2c_adapter *adap)  		 && (timeout++ < MAX_TIMEOUT));  	/* If the SMBus is still busy, we give up */ -	if (timeout >= MAX_TIMEOUT) { +	if (timeout > MAX_TIMEOUT) {  		result = -ETIMEDOUT;  		dev_err(&adap->dev, "SMBus Timeout!\n");  	} diff --git a/drivers/i2c/busses/i2c-amd756.c b/drivers/i2c/busses/i2c-amd756.c index 220f4a1eee1..f7d6fe9c49b 100644 --- a/drivers/i2c/busses/i2c-amd756.c +++ b/drivers/i2c/busses/i2c-amd756.c @@ -126,7 +126,7 @@ static int amd756_transaction(struct i2c_adapter *adap)  		} while ((temp & (GS_HST_STS | GS_SMB_STS)) &&  		         (timeout++ < MAX_TIMEOUT));  		/* If the SMBus is still busy, we give up */ -		if (timeout >= MAX_TIMEOUT) { +		if (timeout > MAX_TIMEOUT) {  			dev_dbg(&adap->dev, "Busy wait timeout (%04x)\n", temp);  			goto abort;  		} @@ -143,7 +143,7 @@ static int amd756_transaction(struct i2c_adapter *adap)  	} while ((temp & GS_HST_STS) && (timeout++ < MAX_TIMEOUT));  	/* If the SMBus is still busy, we give up */ -	if (timeout >= MAX_TIMEOUT) { +	if (timeout > MAX_TIMEOUT) {  		dev_dbg(&adap->dev, "Completion timeout!\n");  		goto abort;  	} diff --git a/drivers/i2c/busses/i2c-at91.c b/drivers/i2c/busses/i2c-at91.c index 67d9dc5b351..06e1ecb4919 100644 --- a/drivers/i2c/busses/i2c-at91.c +++ b/drivers/i2c/busses/i2c-at91.c @@ -200,10 +200,10 @@ static int __devinit at91_i2c_probe(struct platform_device *pdev)  	if (!res)  		return -ENXIO; -	if (!request_mem_region(res->start, res->end - res->start + 1, "at91_i2c")) +	if (!request_mem_region(res->start, resource_size(res), "at91_i2c"))  		return -EBUSY; -	twi_base = ioremap(res->start, res->end - res->start + 1); +	twi_base = ioremap(res->start, resource_size(res));  	if (!twi_base) {  		rc = -ENOMEM;  		goto fail0; @@ -252,7 +252,7 @@ fail2:  fail1:  	iounmap(twi_base);  fail0: -	release_mem_region(res->start, res->end - res->start + 1); +	release_mem_region(res->start, resource_size(res));  	return rc;  } @@ -268,7 +268,7 @@ static int __devexit at91_i2c_remove(struct platform_device *pdev)  	res = platform_get_resource(pdev, IORESOURCE_MEM, 0);  	iounmap(twi_base); -	release_mem_region(res->start, res->end - res->start + 1); +	release_mem_region(res->start, resource_size(res));  	clk_disable(twi_clk);		/* disable peripheral clock */  	clk_put(twi_clk); diff --git a/drivers/i2c/busses/i2c-au1550.c b/drivers/i2c/busses/i2c-au1550.c index f78ce523e3d..532828bc50e 100644 --- a/drivers/i2c/busses/i2c-au1550.c +++ b/drivers/i2c/busses/i2c-au1550.c @@ -389,7 +389,7 @@ i2c_au1550_probe(struct platform_device *pdev)  		goto out;  	} -	priv->ioarea = request_mem_region(r->start, r->end - r->start + 1, +	priv->ioarea = request_mem_region(r->start, resource_size(r),  					  pdev->name);  	if (!priv->ioarea) {  		ret = -EBUSY; diff --git a/drivers/i2c/busses/i2c-bfin-twi.c b/drivers/i2c/busses/i2c-bfin-twi.c index fc548b3d002..b309ac2c3d5 100644 --- a/drivers/i2c/busses/i2c-bfin-twi.c +++ b/drivers/i2c/busses/i2c-bfin-twi.c @@ -12,6 +12,7 @@  #include <linux/kernel.h>  #include <linux/init.h>  #include <linux/i2c.h> +#include <linux/io.h>  #include <linux/mm.h>  #include <linux/timer.h>  #include <linux/spinlock.h> @@ -104,9 +105,14 @@ static void bfin_twi_handle_interrupt(struct bfin_twi_iface *iface)  			write_MASTER_CTL(iface,  				read_MASTER_CTL(iface) | STOP);  		else if (iface->cur_mode == TWI_I2C_MODE_REPEAT && -				iface->cur_msg+1 < iface->msg_num) -			write_MASTER_CTL(iface, -				read_MASTER_CTL(iface) | RSTART); +		         iface->cur_msg + 1 < iface->msg_num) { +			if (iface->pmsg[iface->cur_msg + 1].flags & I2C_M_RD) +				write_MASTER_CTL(iface, +					read_MASTER_CTL(iface) | RSTART | MDIR); +			else +				write_MASTER_CTL(iface, +					(read_MASTER_CTL(iface) | RSTART) & ~MDIR); +		}  		SSYNC();  		/* Clear status */  		write_INT_STAT(iface, XMTSERV); @@ -134,9 +140,13 @@ static void bfin_twi_handle_interrupt(struct bfin_twi_iface *iface)  				read_MASTER_CTL(iface) | STOP);  			SSYNC();  		} else if (iface->cur_mode == TWI_I2C_MODE_REPEAT && -				iface->cur_msg+1 < iface->msg_num) { -			write_MASTER_CTL(iface, -				read_MASTER_CTL(iface) | RSTART); +		           iface->cur_msg + 1 < iface->msg_num) { +			if (iface->pmsg[iface->cur_msg + 1].flags & I2C_M_RD) +				write_MASTER_CTL(iface, +					read_MASTER_CTL(iface) | RSTART | MDIR); +			else +				write_MASTER_CTL(iface, +					(read_MASTER_CTL(iface) | RSTART) & ~MDIR);  			SSYNC();  		}  		/* Clear interrupt source */ @@ -196,8 +206,6 @@ static void bfin_twi_handle_interrupt(struct bfin_twi_iface *iface)  			/* remove restart bit and enable master receive */  			write_MASTER_CTL(iface,  				read_MASTER_CTL(iface) & ~RSTART); -			write_MASTER_CTL(iface, -				read_MASTER_CTL(iface) | MEN | MDIR);  			SSYNC();  		} else if (iface->cur_mode == TWI_I2C_MODE_REPEAT &&  				iface->cur_msg+1 < iface->msg_num) { @@ -222,18 +230,19 @@ static void bfin_twi_handle_interrupt(struct bfin_twi_iface *iface)  			}  			if (iface->pmsg[iface->cur_msg].len <= 255) -				write_MASTER_CTL(iface, -				iface->pmsg[iface->cur_msg].len << 6); +					write_MASTER_CTL(iface, +					(read_MASTER_CTL(iface) & +					(~(0xff << 6))) | +				(iface->pmsg[iface->cur_msg].len << 6));  			else { -				write_MASTER_CTL(iface, 0xff << 6); +				write_MASTER_CTL(iface, +					(read_MASTER_CTL(iface) | +					(0xff << 6)));  				iface->manual_stop = 1;  			}  			/* remove restart bit and enable master receive */  			write_MASTER_CTL(iface,  				read_MASTER_CTL(iface) & ~RSTART); -			write_MASTER_CTL(iface, read_MASTER_CTL(iface) | -				MEN | ((iface->read_write == I2C_SMBUS_READ) ? -				MDIR : 0));  			SSYNC();  		} else {  			iface->result = 1; @@ -441,6 +450,16 @@ int bfin_twi_smbus_xfer(struct i2c_adapter *adap, u16 addr,  		}  		iface->transPtr = data->block;  		break; +	case I2C_SMBUS_I2C_BLOCK_DATA: +		if (read_write == I2C_SMBUS_READ) { +			iface->readNum = data->block[0]; +			iface->cur_mode = TWI_I2C_MODE_COMBINED; +		} else { +			iface->writeNum = data->block[0]; +			iface->cur_mode = TWI_I2C_MODE_STANDARDSUB; +		} +		iface->transPtr = (u8 *)&data->block[1]; +		break;  	default:  		return -1;  	} @@ -564,7 +583,7 @@ static u32 bfin_twi_functionality(struct i2c_adapter *adap)  	return I2C_FUNC_SMBUS_QUICK | I2C_FUNC_SMBUS_BYTE |  	       I2C_FUNC_SMBUS_BYTE_DATA | I2C_FUNC_SMBUS_WORD_DATA |  	       I2C_FUNC_SMBUS_BLOCK_DATA | I2C_FUNC_SMBUS_PROC_CALL | -	       I2C_FUNC_I2C; +	       I2C_FUNC_I2C | I2C_FUNC_SMBUS_I2C_BLOCK;  }  static struct i2c_algorithm bfin_twi_algorithm = { @@ -614,6 +633,7 @@ static int i2c_bfin_twi_probe(struct platform_device *pdev)  	struct i2c_adapter *p_adap;  	struct resource *res;  	int rc; +	unsigned int clkhilow;  	iface = kzalloc(sizeof(struct bfin_twi_iface), GFP_KERNEL);  	if (!iface) { @@ -632,7 +652,7 @@ static int i2c_bfin_twi_probe(struct platform_device *pdev)  		goto out_error_get_res;  	} -	iface->regs_base = ioremap(res->start, res->end - res->start + 1); +	iface->regs_base = ioremap(res->start, resource_size(res));  	if (iface->regs_base == NULL) {  		dev_err(&pdev->dev, "Cannot map IO\n");  		rc = -ENXIO; @@ -675,10 +695,14 @@ static int i2c_bfin_twi_probe(struct platform_device *pdev)  	/* Set TWI internal clock as 10MHz */  	write_CONTROL(iface, ((get_sclk() / 1024 / 1024 + 5) / 10) & 0x7F); +	/* +	 * We will not end up with a CLKDIV=0 because no one will specify +	 * 20kHz SCL or less in Kconfig now. (5 * 1024 / 20 = 0x100) +	 */ +	clkhilow = 5 * 1024 / CONFIG_I2C_BLACKFIN_TWI_CLK_KHZ; +  	/* Set Twi interface clock as specified */ -	write_CLKDIV(iface, ((5*1024 / CONFIG_I2C_BLACKFIN_TWI_CLK_KHZ) -			<< 8) | ((5*1024 / CONFIG_I2C_BLACKFIN_TWI_CLK_KHZ) -			& 0xFF)); +	write_CLKDIV(iface, (clkhilow << 8) | clkhilow);  	/* Enable TWI */  	write_CONTROL(iface, read_CONTROL(iface) | TWI_ENA); diff --git a/drivers/i2c/busses/i2c-cpm.c b/drivers/i2c/busses/i2c-cpm.c index 3fcf78e906d..9c2e10082b7 100644 --- a/drivers/i2c/busses/i2c-cpm.c +++ b/drivers/i2c/busses/i2c-cpm.c @@ -140,7 +140,7 @@ static irqreturn_t cpm_i2c_interrupt(int irq, void *dev_id)  	dev_dbg(&adap->dev, "Interrupt: %x\n", i); -	wake_up_interruptible(&cpm->i2c_wait); +	wake_up(&cpm->i2c_wait);  	return i ? IRQ_HANDLED : IRQ_NONE;  } @@ -364,12 +364,12 @@ static int cpm_i2c_xfer(struct i2c_adapter *adap, struct i2c_msg *msgs, int num)  		dev_dbg(&adap->dev, "test ready.\n");  		pmsg = &msgs[tptr];  		if (pmsg->flags & I2C_M_RD) -			ret = wait_event_interruptible_timeout(cpm->i2c_wait, +			ret = wait_event_timeout(cpm->i2c_wait,  				(in_be16(&tbdf[tptr].cbd_sc) & BD_SC_NAK) ||  				!(in_be16(&rbdf[rptr].cbd_sc) & BD_SC_EMPTY),  				1 * HZ);  		else -			ret = wait_event_interruptible_timeout(cpm->i2c_wait, +			ret = wait_event_timeout(cpm->i2c_wait,  				!(in_be16(&tbdf[tptr].cbd_sc) & BD_SC_READY),  				1 * HZ);  		if (ret == 0) { @@ -531,16 +531,16 @@ static int __devinit cpm_i2c_setup(struct cpm_i2c *cpm)  	rbdf = cpm->rbase;  	for (i = 0; i < CPM_MAXBD; i++) { -		cpm->rxbuf[i] = dma_alloc_coherent( -			NULL, CPM_MAX_READ + 1, &cpm->rxdma[i], GFP_KERNEL); +		cpm->rxbuf[i] = dma_alloc_coherent(&cpm->ofdev->dev, +						   CPM_MAX_READ + 1, +						   &cpm->rxdma[i], GFP_KERNEL);  		if (!cpm->rxbuf[i]) {  			ret = -ENOMEM;  			goto out_muram;  		}  		out_be32(&rbdf[i].cbd_bufaddr, ((cpm->rxdma[i] + 1) & ~1)); -		cpm->txbuf[i] = (unsigned char *)dma_alloc_coherent( -			NULL, CPM_MAX_READ + 1, &cpm->txdma[i], GFP_KERNEL); +		cpm->txbuf[i] = (unsigned char *)dma_alloc_coherent(&cpm->ofdev->dev, CPM_MAX_READ + 1, &cpm->txdma[i], GFP_KERNEL);  		if (!cpm->txbuf[i]) {  			ret = -ENOMEM;  			goto out_muram; @@ -585,10 +585,10 @@ static int __devinit cpm_i2c_setup(struct cpm_i2c *cpm)  out_muram:  	for (i = 0; i < CPM_MAXBD; i++) {  		if (cpm->rxbuf[i]) -			dma_free_coherent(NULL, CPM_MAX_READ + 1, +			dma_free_coherent(&cpm->ofdev->dev, CPM_MAX_READ + 1,  				cpm->rxbuf[i], cpm->rxdma[i]);  		if (cpm->txbuf[i]) -			dma_free_coherent(NULL, CPM_MAX_READ + 1, +			dma_free_coherent(&cpm->ofdev->dev, CPM_MAX_READ + 1,  				cpm->txbuf[i], cpm->txdma[i]);  	}  	cpm_muram_free(cpm->dp_addr); @@ -619,9 +619,9 @@ static void cpm_i2c_shutdown(struct cpm_i2c *cpm)  	/* Free all memory */  	for (i = 0; i < CPM_MAXBD; i++) { -		dma_free_coherent(NULL, CPM_MAX_READ + 1, +		dma_free_coherent(&cpm->ofdev->dev, CPM_MAX_READ + 1,  			cpm->rxbuf[i], cpm->rxdma[i]); -		dma_free_coherent(NULL, CPM_MAX_READ + 1, +		dma_free_coherent(&cpm->ofdev->dev, CPM_MAX_READ + 1,  			cpm->txbuf[i], cpm->txdma[i]);  	} diff --git a/drivers/i2c/busses/i2c-highlander.c b/drivers/i2c/busses/i2c-highlander.c index e5a8dae4a28..87ecace415d 100644 --- a/drivers/i2c/busses/i2c-highlander.c +++ b/drivers/i2c/busses/i2c-highlander.c @@ -373,7 +373,7 @@ static int __devinit highlander_i2c_probe(struct platform_device *pdev)  	if (unlikely(!dev))  		return -ENOMEM; -	dev->base = ioremap_nocache(res->start, res->end - res->start + 1); +	dev->base = ioremap_nocache(res->start, resource_size(res));  	if (unlikely(!dev->base)) {  		ret = -ENXIO;  		goto err; diff --git a/drivers/i2c/busses/i2c-i801.c b/drivers/i2c/busses/i2c-i801.c index 10411848fd7..9d2c5adf5d4 100644 --- a/drivers/i2c/busses/i2c-i801.c +++ b/drivers/i2c/busses/i2c-i801.c @@ -237,7 +237,7 @@ static int i801_transaction(int xact)  		status = inb_p(SMBHSTSTS);  	} while ((status & SMBHSTSTS_HOST_BUSY) && (timeout++ < MAX_TIMEOUT)); -	result = i801_check_post(status, timeout >= MAX_TIMEOUT); +	result = i801_check_post(status, timeout > MAX_TIMEOUT);  	if (result < 0)  		return result; @@ -257,9 +257,9 @@ static void i801_wait_hwpec(void)  	} while ((!(status & SMBHSTSTS_INTR))  		 && (timeout++ < MAX_TIMEOUT)); -	if (timeout >= MAX_TIMEOUT) { +	if (timeout > MAX_TIMEOUT)  		dev_dbg(&I801_dev->dev, "PEC Timeout!\n"); -	} +  	outb_p(status, SMBHSTSTS);  } @@ -344,7 +344,7 @@ static int i801_block_transaction_byte_by_byte(union i2c_smbus_data *data,  		while ((!(status & SMBHSTSTS_BYTE_DONE))  		       && (timeout++ < MAX_TIMEOUT)); -		result = i801_check_post(status, timeout >= MAX_TIMEOUT); +		result = i801_check_post(status, timeout > MAX_TIMEOUT);  		if (result < 0)  			return result; diff --git a/drivers/i2c/busses/i2c-ibm_iic.c b/drivers/i2c/busses/i2c-ibm_iic.c index 8b92a4666e0..e4476743f20 100644 --- a/drivers/i2c/busses/i2c-ibm_iic.c +++ b/drivers/i2c/busses/i2c-ibm_iic.c @@ -756,12 +756,12 @@ static int __devinit iic_probe(struct of_device *ofdev,  		goto error_cleanup;  	} -	/* Now register all the child nodes */ -	of_register_i2c_devices(adap, np); -  	dev_info(&ofdev->dev, "using %s mode\n",  		 dev->fast_mode ? "fast (400 kHz)" : "standard (100 kHz)"); +	/* Now register all the child nodes */ +	of_register_i2c_devices(adap, np); +  	return 0;  error_cleanup: diff --git a/drivers/i2c/busses/i2c-isch.c b/drivers/i2c/busses/i2c-isch.c index b9c01aa9003..9f6b8e0f863 100644 --- a/drivers/i2c/busses/i2c-isch.c +++ b/drivers/i2c/busses/i2c-isch.c @@ -112,7 +112,7 @@ static int sch_transaction(void)  	} while ((temp & 0x08) && (timeout++ < MAX_TIMEOUT));  	/* If the SMBus is still busy, we give up */ -	if (timeout >= MAX_TIMEOUT) { +	if (timeout > MAX_TIMEOUT) {  		dev_err(&sch_adapter.dev, "SMBus Timeout!\n");  		result = -ETIMEDOUT;  	} diff --git a/drivers/i2c/busses/i2c-mpc.c b/drivers/i2c/busses/i2c-mpc.c index 4af5c09f0e8..d325e86e310 100644 --- a/drivers/i2c/busses/i2c-mpc.c +++ b/drivers/i2c/busses/i2c-mpc.c @@ -164,7 +164,7 @@ static int i2c_wait(struct mpc_i2c *i2c, unsigned timeout, int writing)  	return 0;  } -#ifdef CONFIG_PPC_52xx +#ifdef CONFIG_PPC_MPC52xx  static const struct mpc_i2c_divider mpc_i2c_dividers_52xx[] = {  	{20, 0x20}, {22, 0x21}, {24, 0x22}, {26, 0x23},  	{28, 0x24}, {30, 0x01}, {32, 0x25}, {34, 0x02}, @@ -188,7 +188,7 @@ static const struct mpc_i2c_divider mpc_i2c_dividers_52xx[] = {  int mpc_i2c_get_fdr_52xx(struct device_node *node, u32 clock, int prescaler)  { -	const struct mpc52xx_i2c_divider *div = NULL; +	const struct mpc_i2c_divider *div = NULL;  	unsigned int pvr = mfspr(SPRN_PVR);  	u32 divider;  	int i; @@ -197,13 +197,13 @@ int mpc_i2c_get_fdr_52xx(struct device_node *node, u32 clock, int prescaler)  		return -EINVAL;  	/* Determine divider value */ -	divider = mpc52xx_find_ipb_freq(node) / clock; +	divider = mpc5xxx_get_bus_frequency(node) / clock;  	/*  	 * We want to choose an FDR/DFSR that generates an I2C bus speed that  	 * is equal to or lower than the requested speed.  	 */ -	for (i = 0; i < ARRAY_SIZE(mpc52xx_i2c_dividers); i++) { +	for (i = 0; i < ARRAY_SIZE(mpc_i2c_dividers_52xx); i++) {  		div = &mpc_i2c_dividers_52xx[i];  		/* Old MPC5200 rev A CPUs do not support the high bits */  		if (div->fdr & 0xc0 && pvr == 0x80822011) @@ -219,20 +219,23 @@ static void mpc_i2c_setclock_52xx(struct device_node *node,  				  struct mpc_i2c *i2c,  				  u32 clock, u32 prescaler)  { -	int fdr = mpc52xx_i2c_get_fdr(node, clock, prescaler); +	int ret, fdr; + +	ret = mpc_i2c_get_fdr_52xx(node, clock, prescaler); +	fdr = (ret >= 0) ? ret : 0x3f; /* backward compatibility */ -	if (fdr < 0) -		fdr = 0x3f; /* backward compatibility */  	writeb(fdr & 0xff, i2c->base + MPC_I2C_FDR); -	dev_info(i2c->dev, "clock %d Hz (fdr=%d)\n", clock, fdr); + +	if (ret >= 0) +		dev_info(i2c->dev, "clock %d Hz (fdr=%d)\n", clock, fdr);  } -#else /* !CONFIG_PPC_52xx */ +#else /* !CONFIG_PPC_MPC52xx */  static void mpc_i2c_setclock_52xx(struct device_node *node,  				  struct mpc_i2c *i2c,  				  u32 clock, u32 prescaler)  {  } -#endif /* CONFIG_PPC_52xx*/ +#endif /* CONFIG_PPC_MPC52xx*/  #ifdef CONFIG_FSL_SOC  static const struct mpc_i2c_divider mpc_i2c_dividers_8xxx[] = { @@ -321,14 +324,17 @@ static void mpc_i2c_setclock_8xxx(struct device_node *node,  				  struct mpc_i2c *i2c,  				  u32 clock, u32 prescaler)  { -	int fdr = mpc_i2c_get_fdr_8xxx(node, clock, prescaler); +	int ret, fdr; + +	ret = mpc_i2c_get_fdr_8xxx(node, clock, prescaler); +	fdr = (ret >= 0) ? ret : 0x1031; /* backward compatibility */ -	if (fdr < 0) -		fdr = 0x1031; /* backward compatibility */  	writeb(fdr & 0xff, i2c->base + MPC_I2C_FDR);  	writeb((fdr >> 8) & 0xff, i2c->base + MPC_I2C_DFSRR); -	dev_info(i2c->dev, "clock %d Hz (dfsrr=%d fdr=%d)\n", -		 clock, fdr >> 8, fdr & 0xff); + +	if (ret >= 0) +		dev_info(i2c->dev, "clock %d Hz (dfsrr=%d fdr=%d)\n", +			 clock, fdr >> 8, fdr & 0xff);  }  #else /* !CONFIG_FSL_SOC */ diff --git a/drivers/i2c/busses/i2c-mv64xxx.c b/drivers/i2c/busses/i2c-mv64xxx.c index 5a4945d1dba..c3869d94ad4 100644 --- a/drivers/i2c/busses/i2c-mv64xxx.c +++ b/drivers/i2c/busses/i2c-mv64xxx.c @@ -469,7 +469,7 @@ mv64xxx_i2c_map_regs(struct platform_device *pd,  	if (!r)  		return -ENODEV; -	size = r->end - r->start + 1; +	size = resource_size(r);  	if (!request_mem_region(r->start, size, drv_data->adapter.name))  		return -EBUSY; diff --git a/drivers/i2c/busses/i2c-nforce2.c b/drivers/i2c/busses/i2c-nforce2.c index 2ff4683703a..ec11d1c4e77 100644 --- a/drivers/i2c/busses/i2c-nforce2.c +++ b/drivers/i2c/busses/i2c-nforce2.c @@ -173,7 +173,7 @@ static int nforce2_check_status(struct i2c_adapter *adap)  		temp = inb_p(NVIDIA_SMB_STS);  	} while ((!temp) && (timeout++ < MAX_TIMEOUT)); -	if (timeout >= MAX_TIMEOUT) { +	if (timeout > MAX_TIMEOUT) {  		dev_dbg(&adap->dev, "SMBus Timeout!\n");  		if (smbus->can_abort)  			nforce2_abort(adap); diff --git a/drivers/i2c/busses/i2c-ocores.c b/drivers/i2c/busses/i2c-ocores.c index e5193bf7548..0dabe643ec5 100644 --- a/drivers/i2c/busses/i2c-ocores.c +++ b/drivers/i2c/busses/i2c-ocores.c @@ -216,6 +216,7 @@ static int __devinit ocores_i2c_probe(struct platform_device *pdev)  	struct ocores_i2c_platform_data *pdata;  	struct resource *res, *res2;  	int ret; +	int i;  	res = platform_get_resource(pdev, IORESOURCE_MEM, 0);  	if (!res) @@ -233,14 +234,14 @@ static int __devinit ocores_i2c_probe(struct platform_device *pdev)  	if (!i2c)  		return -ENOMEM; -	if (!request_mem_region(res->start, res->end - res->start + 1, +	if (!request_mem_region(res->start, resource_size(res),  				pdev->name)) {  		dev_err(&pdev->dev, "Memory region busy\n");  		ret = -EBUSY;  		goto request_mem_failed;  	} -	i2c->base = ioremap(res->start, res->end - res->start + 1); +	i2c->base = ioremap(res->start, resource_size(res));  	if (!i2c->base) {  		dev_err(&pdev->dev, "Unable to map registers\n");  		ret = -EIO; @@ -271,6 +272,10 @@ static int __devinit ocores_i2c_probe(struct platform_device *pdev)  		goto add_adapter_failed;  	} +	/* add in known devices to the bus */ +	for (i = 0; i < pdata->num_devices; i++) +		i2c_new_device(&i2c->adap, pdata->devices + i); +  	return 0;  add_adapter_failed: @@ -278,7 +283,7 @@ add_adapter_failed:  request_irq_failed:  	iounmap(i2c->base);  map_failed: -	release_mem_region(res->start, res->end - res->start + 1); +	release_mem_region(res->start, resource_size(res));  request_mem_failed:  	kfree(i2c); @@ -306,7 +311,7 @@ static int __devexit ocores_i2c_remove(struct platform_device* pdev)  	res = platform_get_resource(pdev, IORESOURCE_MEM, 0);  	if (res) -		release_mem_region(res->start, res->end - res->start + 1); +		release_mem_region(res->start, resource_size(res));  	kfree(i2c); diff --git a/drivers/i2c/busses/i2c-omap.c b/drivers/i2c/busses/i2c-omap.c index ece0125a1ee..ad8d2010c92 100644 --- a/drivers/i2c/busses/i2c-omap.c +++ b/drivers/i2c/busses/i2c-omap.c @@ -333,8 +333,18 @@ static int omap_i2c_init(struct omap_i2c_dev *dev)  	if (cpu_is_omap2430() || cpu_is_omap34xx()) { -		/* HSI2C controller internal clk rate should be 19.2 Mhz */ -		internal_clk = 19200; +		/* +		 * HSI2C controller internal clk rate should be 19.2 Mhz for +		 * HS and for all modes on 2430. On 34xx we can use lower rate +		 * to get longer filter period for better noise suppression. +		 * The filter is iclk (fclk for HS) period. +		 */ +		if (dev->speed > 400 || cpu_is_omap2430()) +			internal_clk = 19200; +		else if (dev->speed > 100) +			internal_clk = 9600; +		else +			internal_clk = 4000;  		fclk_rate = clk_get_rate(dev->fclk) / 1000;  		/* Compute prescaler divisor */ @@ -343,17 +353,28 @@ static int omap_i2c_init(struct omap_i2c_dev *dev)  		/* If configured for High Speed */  		if (dev->speed > 400) { +			unsigned long scl; +  			/* For first phase of HS mode */ -			fsscll = internal_clk / (400 * 2) - 6; -			fssclh = internal_clk / (400 * 2) - 6; +			scl = internal_clk / 400; +			fsscll = scl - (scl / 3) - 7; +			fssclh = (scl / 3) - 5;  			/* For second phase of HS mode */ -			hsscll = fclk_rate / (dev->speed * 2) - 6; -			hssclh = fclk_rate / (dev->speed * 2) - 6; +			scl = fclk_rate / dev->speed; +			hsscll = scl - (scl / 3) - 7; +			hssclh = (scl / 3) - 5; +		} else if (dev->speed > 100) { +			unsigned long scl; + +			/* Fast mode */ +			scl = internal_clk / dev->speed; +			fsscll = scl - (scl / 3) - 7; +			fssclh = (scl / 3) - 5;  		} else { -			/* To handle F/S modes */ -			fsscll = internal_clk / (dev->speed * 2) - 6; -			fssclh = internal_clk / (dev->speed * 2) - 6; +			/* Standard mode */ +			fsscll = internal_clk / (dev->speed * 2) - 7; +			fssclh = internal_clk / (dev->speed * 2) - 5;  		}  		scll = (hsscll << OMAP_I2C_SCLL_HSSCLL) | fsscll;  		sclh = (hssclh << OMAP_I2C_SCLH_HSSCLH) | fssclh; @@ -807,7 +828,7 @@ omap_i2c_probe(struct platform_device *pdev)  	dev->idle = 1;  	dev->dev = &pdev->dev;  	dev->irq = irq->start; -	dev->base = ioremap(mem->start, mem->end - mem->start + 1); +	dev->base = ioremap(mem->start, resource_size(mem));  	if (!dev->base) {  		r = -ENOMEM;  		goto err_free_mem; diff --git a/drivers/i2c/busses/i2c-pca-platform.c b/drivers/i2c/busses/i2c-pca-platform.c index 7b23891b7d5..c4df9d411cd 100644 --- a/drivers/i2c/busses/i2c-pca-platform.c +++ b/drivers/i2c/busses/i2c-pca-platform.c @@ -27,8 +27,6 @@  #include <asm/irq.h>  #include <asm/io.h> -#define res_len(r)		((r)->end - (r)->start + 1) -  struct i2c_pca_pf_data {  	void __iomem			*reg_base;  	int				irq;	/* if 0, use polling */ @@ -148,7 +146,7 @@ static int __devinit i2c_pca_pf_probe(struct platform_device *pdev)  		goto e_print;  	} -	if (!request_mem_region(res->start, res_len(res), res->name)) { +	if (!request_mem_region(res->start, resource_size(res), res->name)) {  		ret = -ENOMEM;  		goto e_print;  	} @@ -161,13 +159,13 @@ static int __devinit i2c_pca_pf_probe(struct platform_device *pdev)  	init_waitqueue_head(&i2c->wait); -	i2c->reg_base = ioremap(res->start, res_len(res)); +	i2c->reg_base = ioremap(res->start, resource_size(res));  	if (!i2c->reg_base) {  		ret = -ENOMEM;  		goto e_remap;  	}  	i2c->io_base = res->start; -	i2c->io_size = res_len(res); +	i2c->io_size = resource_size(res);  	i2c->irq = irq;  	i2c->adap.nr = pdev->id >= 0 ? pdev->id : 0; @@ -250,7 +248,7 @@ e_reqirq:  e_remap:  	kfree(i2c);  e_alloc: -	release_mem_region(res->start, res_len(res)); +	release_mem_region(res->start, resource_size(res));  e_print:  	printk(KERN_ERR "Registering PCA9564/PCA9665 FAILED! (%d)\n", ret);  	return ret; diff --git a/drivers/i2c/busses/i2c-pmcmsp.c b/drivers/i2c/busses/i2c-pmcmsp.c index 0bdb2d7f057..7b57d5f267e 100644 --- a/drivers/i2c/busses/i2c-pmcmsp.c +++ b/drivers/i2c/busses/i2c-pmcmsp.c @@ -283,7 +283,7 @@ static int __devinit pmcmsptwi_probe(struct platform_device *pldev)  	}  	/* reserve the memory region */ -	if (!request_mem_region(res->start, res->end - res->start + 1, +	if (!request_mem_region(res->start, resource_size(res),  				pldev->name)) {  		dev_err(&pldev->dev,  			"Unable to get memory/io address region 0x%08x\n", @@ -294,7 +294,7 @@ static int __devinit pmcmsptwi_probe(struct platform_device *pldev)  	/* remap the memory */  	pmcmsptwi_data.iobase = ioremap_nocache(res->start, -						res->end - res->start + 1); +						resource_size(res));  	if (!pmcmsptwi_data.iobase) {  		dev_err(&pldev->dev,  			"Unable to ioremap address 0x%08x\n", res->start); @@ -360,7 +360,7 @@ ret_unmap:  	iounmap(pmcmsptwi_data.iobase);  ret_unreserve: -	release_mem_region(res->start, res->end - res->start + 1); +	release_mem_region(res->start, resource_size(res));  ret_err:  	return rc; @@ -385,7 +385,7 @@ static int __devexit pmcmsptwi_remove(struct platform_device *pldev)  	iounmap(pmcmsptwi_data.iobase);  	res = platform_get_resource(pldev, IORESOURCE_MEM, 0); -	release_mem_region(res->start, res->end - res->start + 1); +	release_mem_region(res->start, resource_size(res));  	return 0;  } diff --git a/drivers/i2c/busses/i2c-pxa.c b/drivers/i2c/busses/i2c-pxa.c index c1405c8f6ba..762e1e53088 100644 --- a/drivers/i2c/busses/i2c-pxa.c +++ b/drivers/i2c/busses/i2c-pxa.c @@ -34,10 +34,24 @@  #include <linux/err.h>  #include <linux/clk.h> -#include <mach/hardware.h>  #include <asm/irq.h>  #include <asm/io.h> -#include <mach/i2c.h> +#include <plat/i2c.h> + +/* + * I2C register offsets will be shifted 0 or 1 bit left, depending on + * different SoCs + */ +#define REG_SHIFT_0	(0 << 0) +#define REG_SHIFT_1	(1 << 0) +#define REG_SHIFT(d)	((d) & 0x1) + +static const struct platform_device_id i2c_pxa_id_table[] = { +	{ "pxa2xx-i2c",		REG_SHIFT_1 }, +	{ "pxa3xx-pwri2c",	REG_SHIFT_0 }, +	{ }, +}; +MODULE_DEVICE_TABLE(platform, i2c_pxa_id_table);  /*   * I2C registers and bit definitions @@ -265,10 +279,10 @@ static int i2c_pxa_wait_bus_not_busy(struct pxa_i2c *i2c)  		show_state(i2c);  	} -	if (timeout <= 0) +	if (timeout < 0)  		show_state(i2c); -	return timeout <= 0 ? I2C_RETRY : 0; +	return timeout < 0 ? I2C_RETRY : 0;  }  static int i2c_pxa_wait_master(struct pxa_i2c *i2c) @@ -612,7 +626,7 @@ static int i2c_pxa_pio_set_master(struct pxa_i2c *i2c)  		show_state(i2c);  	} -	if (timeout <= 0) { +	if (timeout < 0) {  		show_state(i2c);  		dev_err(&i2c->adap.dev,  			"i2c_pxa: timeout waiting for bus free\n"); @@ -979,12 +993,12 @@ static const struct i2c_algorithm i2c_pxa_pio_algorithm = {  	.functionality	= i2c_pxa_functionality,  }; -#define res_len(r)		((r)->end - (r)->start + 1)  static int i2c_pxa_probe(struct platform_device *dev)  {  	struct pxa_i2c *i2c;  	struct resource *res;  	struct i2c_pxa_platform_data *plat = dev->dev.platform_data; +	struct platform_device_id *id = platform_get_device_id(dev);  	int ret;  	int irq; @@ -993,7 +1007,7 @@ static int i2c_pxa_probe(struct platform_device *dev)  	if (res == NULL || irq < 0)  		return -ENODEV; -	if (!request_mem_region(res->start, res_len(res), res->name)) +	if (!request_mem_region(res->start, resource_size(res), res->name))  		return -ENOMEM;  	i2c = kzalloc(sizeof(struct pxa_i2c), GFP_KERNEL); @@ -1023,15 +1037,15 @@ static int i2c_pxa_probe(struct platform_device *dev)  		goto eclk;  	} -	i2c->reg_base = ioremap(res->start, res_len(res)); +	i2c->reg_base = ioremap(res->start, resource_size(res));  	if (!i2c->reg_base) {  		ret = -EIO;  		goto eremap;  	} -	i2c->reg_shift = (cpu_is_pxa3xx() && (dev->id == 1)) ? 0 : 1; +	i2c->reg_shift = REG_SHIFT(id->driver_data);  	i2c->iobase = res->start; -	i2c->iosize = res_len(res); +	i2c->iosize = resource_size(res);  	i2c->irq = irq; @@ -1095,7 +1109,7 @@ eremap:  eclk:  	kfree(i2c);  emalloc: -	release_mem_region(res->start, res_len(res)); +	release_mem_region(res->start, resource_size(res));  	return ret;  } @@ -1150,6 +1164,7 @@ static struct platform_driver i2c_pxa_driver = {  		.name	= "pxa2xx-i2c",  		.owner	= THIS_MODULE,  	}, +	.id_table	= i2c_pxa_id_table,  };  static int __init i2c_adap_pxa_init(void) diff --git a/drivers/i2c/busses/i2c-s3c2410.c b/drivers/i2c/busses/i2c-s3c2410.c index 1691ef0f1ee..8f42a4536cd 100644 --- a/drivers/i2c/busses/i2c-s3c2410.c +++ b/drivers/i2c/busses/i2c-s3c2410.c @@ -51,6 +51,11 @@ enum s3c24xx_i2c_state {  	STATE_STOP  }; +enum s3c24xx_i2c_type { +	TYPE_S3C2410, +	TYPE_S3C2440, +}; +  struct s3c24xx_i2c {  	spinlock_t		lock;  	wait_queue_head_t	wait; @@ -88,8 +93,10 @@ struct s3c24xx_i2c {  static inline int s3c24xx_i2c_is2440(struct s3c24xx_i2c *i2c)  {  	struct platform_device *pdev = to_platform_device(i2c->dev); +	enum s3c24xx_i2c_type type; -	return !strcmp(pdev->name, "s3c2440-i2c"); +	type = platform_get_device_id(pdev)->driver_data; +	return type == TYPE_S3C2440;  }  /* s3c24xx_i2c_master_complete @@ -821,7 +828,7 @@ static int s3c24xx_i2c_probe(struct platform_device *pdev)  		goto err_clk;  	} -	i2c->ioarea = request_mem_region(res->start, (res->end-res->start)+1, +	i2c->ioarea = request_mem_region(res->start, resource_size(res),  					 pdev->name);  	if (i2c->ioarea == NULL) { @@ -830,7 +837,7 @@ static int s3c24xx_i2c_probe(struct platform_device *pdev)  		goto err_clk;  	} -	i2c->regs = ioremap(res->start, (res->end-res->start)+1); +	i2c->regs = ioremap(res->start, resource_size(res));  	if (i2c->regs == NULL) {  		dev_err(&pdev->dev, "cannot map IO\n"); @@ -969,52 +976,41 @@ static int s3c24xx_i2c_resume(struct platform_device *dev)  /* device driver for platform bus bits */ -static struct platform_driver s3c2410_i2c_driver = { -	.probe		= s3c24xx_i2c_probe, -	.remove		= s3c24xx_i2c_remove, -	.suspend_late	= s3c24xx_i2c_suspend_late, -	.resume		= s3c24xx_i2c_resume, -	.driver		= { -		.owner	= THIS_MODULE, -		.name	= "s3c2410-i2c", -	}, +static struct platform_device_id s3c24xx_driver_ids[] = { +	{ +		.name		= "s3c2410-i2c", +		.driver_data	= TYPE_S3C2410, +	}, { +		.name		= "s3c2440-i2c", +		.driver_data	= TYPE_S3C2440, +	}, { },  }; +MODULE_DEVICE_TABLE(platform, s3c24xx_driver_ids); -static struct platform_driver s3c2440_i2c_driver = { +static struct platform_driver s3c24xx_i2c_driver = {  	.probe		= s3c24xx_i2c_probe,  	.remove		= s3c24xx_i2c_remove,  	.suspend_late	= s3c24xx_i2c_suspend_late,  	.resume		= s3c24xx_i2c_resume, +	.id_table	= s3c24xx_driver_ids,  	.driver		= {  		.owner	= THIS_MODULE, -		.name	= "s3c2440-i2c", +		.name	= "s3c-i2c",  	},  };  static int __init i2c_adap_s3c_init(void)  { -	int ret; - -	ret = platform_driver_register(&s3c2410_i2c_driver); -	if (ret == 0) { -		ret = platform_driver_register(&s3c2440_i2c_driver); -		if (ret) -			platform_driver_unregister(&s3c2410_i2c_driver); -	} - -	return ret; +	return platform_driver_register(&s3c24xx_i2c_driver);  }  subsys_initcall(i2c_adap_s3c_init);  static void __exit i2c_adap_s3c_exit(void)  { -	platform_driver_unregister(&s3c2410_i2c_driver); -	platform_driver_unregister(&s3c2440_i2c_driver); +	platform_driver_unregister(&s3c24xx_i2c_driver);  }  module_exit(i2c_adap_s3c_exit);  MODULE_DESCRIPTION("S3C24XX I2C Bus driver");  MODULE_AUTHOR("Ben Dooks, <ben@simtec.co.uk>");  MODULE_LICENSE("GPL"); -MODULE_ALIAS("platform:s3c2410-i2c"); -MODULE_ALIAS("platform:s3c2440-i2c"); diff --git a/drivers/i2c/busses/i2c-sh7760.c b/drivers/i2c/busses/i2c-sh7760.c index baa28b73ae4..b9680f50f54 100644 --- a/drivers/i2c/busses/i2c-sh7760.c +++ b/drivers/i2c/busses/i2c-sh7760.c @@ -396,7 +396,7 @@ static int __devinit calc_CCR(unsigned long scl_hz)  	signed char cdf, cdfm;  	int scgd, scgdm, scgds; -	mclk = clk_get(NULL, "module_clk"); +	mclk = clk_get(NULL, "peripheral_clk");  	if (IS_ERR(mclk)) {  		return PTR_ERR(mclk);  	} else { diff --git a/drivers/i2c/busses/i2c-sis5595.c b/drivers/i2c/busses/i2c-sis5595.c index f320ab27da4..139f0c7f12a 100644 --- a/drivers/i2c/busses/i2c-sis5595.c +++ b/drivers/i2c/busses/i2c-sis5595.c @@ -256,7 +256,7 @@ static int sis5595_transaction(struct i2c_adapter *adap)  	} while (!(temp & 0x40) && (timeout++ < MAX_TIMEOUT));  	/* If the SMBus is still busy, we give up */ -	if (timeout >= MAX_TIMEOUT) { +	if (timeout > MAX_TIMEOUT) {  		dev_dbg(&adap->dev, "SMBus Timeout!\n");  		result = -ETIMEDOUT;  	} diff --git a/drivers/i2c/busses/i2c-sis630.c b/drivers/i2c/busses/i2c-sis630.c index 50c3610e602..70ca41e90e5 100644 --- a/drivers/i2c/busses/i2c-sis630.c +++ b/drivers/i2c/busses/i2c-sis630.c @@ -173,7 +173,7 @@ static int sis630_transaction_wait(struct i2c_adapter *adap, int size)  	} while (!(temp & 0x0e) && (timeout++ < MAX_TIMEOUT));  	/* If the SMBus is still busy, we give up */ -	if (timeout >= MAX_TIMEOUT) { +	if (timeout > MAX_TIMEOUT) {  		dev_dbg(&adap->dev, "SMBus Timeout!\n");  		result = -ETIMEDOUT;  	} diff --git a/drivers/i2c/busses/i2c-sis96x.c b/drivers/i2c/busses/i2c-sis96x.c index 7e1594b4057..8295885b2fd 100644 --- a/drivers/i2c/busses/i2c-sis96x.c +++ b/drivers/i2c/busses/i2c-sis96x.c @@ -132,7 +132,7 @@ static int sis96x_transaction(int size)  	} while (!(temp & 0x0e) && (timeout++ < MAX_TIMEOUT));  	/* If the SMBus is still busy, we give up */ -	if (timeout >= MAX_TIMEOUT) { +	if (timeout > MAX_TIMEOUT) {  		dev_dbg(&sis96x_adapter.dev, "SMBus Timeout! (0x%02x)\n", temp);  		result = -ETIMEDOUT;  	} diff --git a/drivers/i2c/busses/i2c-stu300.c b/drivers/i2c/busses/i2c-stu300.c new file mode 100644 index 00000000000..182e711318b --- /dev/null +++ b/drivers/i2c/busses/i2c-stu300.c @@ -0,0 +1,1029 @@ +/* + * Copyright (C) 2007-2009 ST-Ericsson AB + * License terms: GNU General Public License (GPL) version 2 + * ST DDC I2C master mode driver, used in e.g. U300 series platforms. + * Author: Linus Walleij <linus.walleij@stericsson.com> + * Author: Jonas Aaberg <jonas.aberg@stericsson.com> + */ +#include <linux/init.h> +#include <linux/module.h> +#include <linux/platform_device.h> +#include <linux/delay.h> +#include <linux/i2c.h> +#include <linux/spinlock.h> +#include <linux/completion.h> +#include <linux/err.h> +#include <linux/interrupt.h> +#include <linux/clk.h> +#include <linux/io.h> + +/* the name of this kernel module */ +#define NAME "stu300" + +/* CR (Control Register) 8bit (R/W) */ +#define I2C_CR					(0x00000000) +#define I2C_CR_RESET_VALUE			(0x00) +#define I2C_CR_RESET_UMASK			(0x00) +#define I2C_CR_DDC1_ENABLE			(0x80) +#define I2C_CR_TRANS_ENABLE			(0x40) +#define I2C_CR_PERIPHERAL_ENABLE		(0x20) +#define I2C_CR_DDC2B_ENABLE			(0x10) +#define I2C_CR_START_ENABLE			(0x08) +#define I2C_CR_ACK_ENABLE			(0x04) +#define I2C_CR_STOP_ENABLE			(0x02) +#define I2C_CR_INTERRUPT_ENABLE			(0x01) +/* SR1 (Status Register 1) 8bit (R/-) */ +#define I2C_SR1					(0x00000004) +#define I2C_SR1_RESET_VALUE			(0x00) +#define I2C_SR1_RESET_UMASK			(0x00) +#define I2C_SR1_EVF_IND				(0x80) +#define I2C_SR1_ADD10_IND			(0x40) +#define I2C_SR1_TRA_IND				(0x20) +#define I2C_SR1_BUSY_IND			(0x10) +#define I2C_SR1_BTF_IND				(0x08) +#define I2C_SR1_ADSL_IND			(0x04) +#define I2C_SR1_MSL_IND				(0x02) +#define I2C_SR1_SB_IND				(0x01) +/* SR2 (Status Register 2) 8bit (R/-) */ +#define I2C_SR2					(0x00000008) +#define I2C_SR2_RESET_VALUE			(0x00) +#define I2C_SR2_RESET_UMASK			(0x40) +#define I2C_SR2_MASK				(0xBF) +#define I2C_SR2_SCLFAL_IND			(0x80) +#define I2C_SR2_ENDAD_IND			(0x20) +#define I2C_SR2_AF_IND				(0x10) +#define I2C_SR2_STOPF_IND			(0x08) +#define I2C_SR2_ARLO_IND			(0x04) +#define I2C_SR2_BERR_IND			(0x02) +#define I2C_SR2_DDC2BF_IND			(0x01) +/* CCR (Clock Control Register) 8bit (R/W) */ +#define I2C_CCR					(0x0000000C) +#define I2C_CCR_RESET_VALUE			(0x00) +#define I2C_CCR_RESET_UMASK			(0x00) +#define I2C_CCR_MASK				(0xFF) +#define I2C_CCR_FMSM				(0x80) +#define I2C_CCR_CC_MASK				(0x7F) +/* OAR1 (Own Address Register 1) 8bit (R/W) */ +#define I2C_OAR1				(0x00000010) +#define I2C_OAR1_RESET_VALUE			(0x00) +#define I2C_OAR1_RESET_UMASK			(0x00) +#define I2C_OAR1_ADD_MASK			(0xFF) +/* OAR2 (Own Address Register 2) 8bit (R/W) */ +#define I2C_OAR2				(0x00000014) +#define I2C_OAR2_RESET_VALUE			(0x40) +#define I2C_OAR2_RESET_UMASK			(0x19) +#define I2C_OAR2_MASK				(0xE6) +#define I2C_OAR2_FR_25_10MHZ			(0x00) +#define I2C_OAR2_FR_10_1667MHZ			(0x20) +#define I2C_OAR2_FR_1667_2667MHZ		(0x40) +#define I2C_OAR2_FR_2667_40MHZ			(0x60) +#define I2C_OAR2_FR_40_5333MHZ			(0x80) +#define I2C_OAR2_FR_5333_66MHZ			(0xA0) +#define I2C_OAR2_FR_66_80MHZ			(0xC0) +#define I2C_OAR2_FR_80_100MHZ			(0xE0) +#define I2C_OAR2_FR_MASK			(0xE0) +#define I2C_OAR2_ADD_MASK			(0x06) +/* DR (Data Register) 8bit (R/W) */ +#define I2C_DR					(0x00000018) +#define I2C_DR_RESET_VALUE			(0x00) +#define I2C_DR_RESET_UMASK			(0xFF) +#define I2C_DR_D_MASK				(0xFF) +/* ECCR (Extended Clock Control Register) 8bit (R/W) */ +#define I2C_ECCR				(0x0000001C) +#define I2C_ECCR_RESET_VALUE			(0x00) +#define I2C_ECCR_RESET_UMASK			(0xE0) +#define I2C_ECCR_MASK				(0x1F) +#define I2C_ECCR_CC_MASK			(0x1F) + +/* + * These events are more or less responses to commands + * sent into the hardware, presumably reflecting the state + * of an internal state machine. + */ +enum stu300_event { +	STU300_EVENT_NONE = 0, +	STU300_EVENT_1, +	STU300_EVENT_2, +	STU300_EVENT_3, +	STU300_EVENT_4, +	STU300_EVENT_5, +	STU300_EVENT_6, +	STU300_EVENT_7, +	STU300_EVENT_8, +	STU300_EVENT_9 +}; + +enum stu300_error { +	STU300_ERROR_NONE = 0, +	STU300_ERROR_ACKNOWLEDGE_FAILURE, +	STU300_ERROR_BUS_ERROR, +	STU300_ERROR_ARBITRATION_LOST +}; + +/* timeout waiting for the controller to respond */ +#define STU300_TIMEOUT (msecs_to_jiffies(1000)) + +/* + * The number of address send athemps tried before giving up. + * If the first one failes it seems like 5 to 8 attempts are required. + */ +#define NUM_ADDR_RESEND_ATTEMPTS 10 + +/* I2C clock speed, in Hz 0-400kHz*/ +static unsigned int scl_frequency = 100000; +module_param(scl_frequency, uint,  0644); + +/** + * struct stu300_dev - the stu300 driver state holder + * @pdev: parent platform device + * @adapter: corresponding I2C adapter + * @phybase: location of I/O area in memory + * @physize: size of I/O area in memory + * @clk: hardware block clock + * @irq: assigned interrupt line + * @cmd_issue_lock: this locks the following cmd_ variables + * @cmd_complete: acknowledge completion for an I2C command + * @cmd_event: expected event coming in as a response to a command + * @cmd_err: error code as response to a command + * @speed: current bus speed in Hz + * @msg_index: index of current message + * @msg_len: length of current message + */ +struct stu300_dev { +	struct platform_device	*pdev; +	struct i2c_adapter	adapter; +	resource_size_t		phybase; +	resource_size_t		physize; +	void __iomem		*virtbase; +	struct clk		*clk; +	int			irq; +	spinlock_t		cmd_issue_lock; +	struct completion	cmd_complete; +	enum stu300_event	cmd_event; +	enum stu300_error	cmd_err; +	unsigned int		speed; +	int			msg_index; +	int			msg_len; +}; + +/* Local forward function declarations */ +static int stu300_init_hw(struct stu300_dev *dev); + +/* + * The block needs writes in both MSW and LSW in order + * for all data lines to reach their destination. + */ +static inline void stu300_wr8(u32 value, void __iomem *address) +{ +	writel((value << 16) | value, address); +} + +/* + * This merely masks off the duplicates which appear + * in bytes 1-3. You _MUST_ use 32-bit bus access on this + * device, else it will not work. + */ +static inline u32 stu300_r8(void __iomem *address) +{ +	return readl(address) & 0x000000FFU; +} + +/* + * Tells whether a certain event or events occurred in + * response to a command. The events represent states in + * the internal state machine of the hardware. The events + * are not very well described in the hardware + * documentation and can only be treated as abstract state + * machine states. + * + * @ret 0 = event has not occurred, any other value means + * the event occurred. + */ +static int stu300_event_occurred(struct stu300_dev *dev, +				   enum stu300_event mr_event) { +	u32 status1; +	u32 status2; + +	/* What event happened? */ +	status1 = stu300_r8(dev->virtbase + I2C_SR1); +	if (!(status1 & I2C_SR1_EVF_IND)) +		/* No event at all */ +		return 0; +	status2 = stu300_r8(dev->virtbase + I2C_SR2); + +	switch (mr_event) { +	case STU300_EVENT_1: +		if (status1 & I2C_SR1_ADSL_IND) +			return 1; +		break; +	case STU300_EVENT_2: +	case STU300_EVENT_3: +	case STU300_EVENT_7: +	case STU300_EVENT_8: +		if (status1 & I2C_SR1_BTF_IND) { +			if (status2 & I2C_SR2_AF_IND) +				dev->cmd_err = STU300_ERROR_ACKNOWLEDGE_FAILURE; +			else if (status2 & I2C_SR2_BERR_IND) +				dev->cmd_err = STU300_ERROR_BUS_ERROR; +			return 1; +		} +		break; +	case STU300_EVENT_4: +		if (status2 & I2C_SR2_STOPF_IND) +			return 1; +		break; +	case STU300_EVENT_5: +		if (status1 & I2C_SR1_SB_IND) +			/* Clear start bit */ +			return 1; +		break; +	case STU300_EVENT_6: +		if (status2 & I2C_SR2_ENDAD_IND) { +			/* First check for any errors */ +			if (status2 & I2C_SR2_AF_IND) +				dev->cmd_err = STU300_ERROR_ACKNOWLEDGE_FAILURE; +			return 1; +		} +		break; +	case STU300_EVENT_9: +		if (status1 & I2C_SR1_ADD10_IND) +			return 1; +		break; +	default: +		break; +	} +	if (status2 & I2C_SR2_ARLO_IND) +		dev->cmd_err = STU300_ERROR_ARBITRATION_LOST; +	return 0; +} + +static irqreturn_t stu300_irh(int irq, void *data) +{ +	struct stu300_dev *dev = data; +	int res; + +	/* See if this was what we were waiting for */ +	spin_lock(&dev->cmd_issue_lock); +	if (dev->cmd_event != STU300_EVENT_NONE) { +		res = stu300_event_occurred(dev, dev->cmd_event); +		if (res || dev->cmd_err != STU300_ERROR_NONE) { +			u32 val; + +			complete(&dev->cmd_complete); +			/* Block any multiple interrupts */ +			val = stu300_r8(dev->virtbase + I2C_CR); +			val &= ~I2C_CR_INTERRUPT_ENABLE; +			stu300_wr8(val, dev->virtbase + I2C_CR); +		} +	} +	spin_unlock(&dev->cmd_issue_lock); +	return IRQ_HANDLED; +} + +/* + * Sends a command and then waits for the bits masked by *flagmask* + * to go high or low by IRQ awaiting. + */ +static int stu300_start_and_await_event(struct stu300_dev *dev, +					  u8 cr_value, +					  enum stu300_event mr_event) +{ +	int ret; + +	if (unlikely(irqs_disabled())) { +		/* TODO: implement polling for this case if need be. */ +		WARN(1, "irqs are disabled, cannot poll for event\n"); +		return -EIO; +	} + +	/* Lock command issue, fill in an event we wait for */ +	spin_lock_irq(&dev->cmd_issue_lock); +	init_completion(&dev->cmd_complete); +	dev->cmd_err = STU300_ERROR_NONE; +	dev->cmd_event = mr_event; +	spin_unlock_irq(&dev->cmd_issue_lock); + +	/* Turn on interrupt, send command and wait. */ +	cr_value |= I2C_CR_INTERRUPT_ENABLE; +	stu300_wr8(cr_value, dev->virtbase + I2C_CR); +	ret = wait_for_completion_interruptible_timeout(&dev->cmd_complete, +							STU300_TIMEOUT); + +	if (ret < 0) { +		dev_err(&dev->pdev->dev, +		       "wait_for_completion_interruptible_timeout() " +		       "returned %d waiting for event %04x\n", ret, mr_event); +		return ret; +	} + +	if (ret == 0) { +		dev_err(&dev->pdev->dev, "controller timed out " +		       "waiting for event %d, reinit hardware\n", mr_event); +		(void) stu300_init_hw(dev); +		return -ETIMEDOUT; +	} + +	if (dev->cmd_err != STU300_ERROR_NONE) { +		dev_err(&dev->pdev->dev, "controller (start) " +		       "error %d waiting for event %d, reinit hardware\n", +		       dev->cmd_err, mr_event); +		(void) stu300_init_hw(dev); +		return -EIO; +	} + +	return 0; +} + +/* + * This waits for a flag to be set, if it is not set on entry, an interrupt is + * configured to wait for the flag using a completion. + */ +static int stu300_await_event(struct stu300_dev *dev, +				enum stu300_event mr_event) +{ +	int ret; +	u32 val; + +	if (unlikely(irqs_disabled())) { +		/* TODO: implement polling for this case if need be. */ +		dev_err(&dev->pdev->dev, "irqs are disabled on this " +			"system!\n"); +		return -EIO; +	} + +	/* Is it already here? */ +	spin_lock_irq(&dev->cmd_issue_lock); +	dev->cmd_err = STU300_ERROR_NONE; +	if (stu300_event_occurred(dev, mr_event)) { +		spin_unlock_irq(&dev->cmd_issue_lock); +		goto exit_await_check_err; +	} +	init_completion(&dev->cmd_complete); +	dev->cmd_err = STU300_ERROR_NONE; +	dev->cmd_event = mr_event; + +	/* Turn on the I2C interrupt for current operation */ +	val = stu300_r8(dev->virtbase + I2C_CR); +	val |= I2C_CR_INTERRUPT_ENABLE; +	stu300_wr8(val, dev->virtbase + I2C_CR); + +	/* Twice paranoia (possible HW glitch) */ +	stu300_wr8(val, dev->virtbase + I2C_CR); + +	/* Check again: is it already here? */ +	if (unlikely(stu300_event_occurred(dev, mr_event))) { +		/* Disable IRQ again. */ +		val &= ~I2C_CR_INTERRUPT_ENABLE; +		stu300_wr8(val, dev->virtbase + I2C_CR); +		spin_unlock_irq(&dev->cmd_issue_lock); +		goto exit_await_check_err; +	} + +	/* Unlock the command block and wait for the event to occur */ +	spin_unlock_irq(&dev->cmd_issue_lock); +	ret = wait_for_completion_interruptible_timeout(&dev->cmd_complete, +							STU300_TIMEOUT); + +	if (ret < 0) { +		dev_err(&dev->pdev->dev, +		       "wait_for_completion_interruptible_timeout()" +		       "returned %d waiting for event %04x\n", ret, mr_event); +		return ret; +	} + +	if (ret == 0) { +		if (mr_event != STU300_EVENT_6) { +			dev_err(&dev->pdev->dev, "controller " +				"timed out waiting for event %d, reinit " +				"hardware\n", mr_event); +			(void) stu300_init_hw(dev); +		} +		return -ETIMEDOUT; +	} + + exit_await_check_err: +	if (dev->cmd_err != STU300_ERROR_NONE) { +		if (mr_event != STU300_EVENT_6) { +			dev_err(&dev->pdev->dev, "controller " +				"error (await_event) %d waiting for event %d, " +			       "reinit hardware\n", dev->cmd_err, mr_event); +			(void) stu300_init_hw(dev); +		} +		return -EIO; +	} + +	return 0; +} + +/* + * Waits for the busy bit to go low by repeated polling. + */ +#define BUSY_RELEASE_ATTEMPTS 10 +static int stu300_wait_while_busy(struct stu300_dev *dev) +{ +	unsigned long timeout; +	int i; + +	for (i = 0; i < BUSY_RELEASE_ATTEMPTS; i++) { +		timeout = jiffies + STU300_TIMEOUT; + +		while (!time_after(jiffies, timeout)) { +			/* Is not busy? */ +			if ((stu300_r8(dev->virtbase + I2C_SR1) & +			     I2C_SR1_BUSY_IND) == 0) +				return 0; +			msleep(1); +		} + +		dev_err(&dev->pdev->dev, "transaction timed out " +			"waiting for device to be free (not busy). " +		       "Attempt: %d\n", i+1); + +		dev_err(&dev->pdev->dev, "base address = " +			"0x%08x, reinit hardware\n", (u32) dev->virtbase); + +		(void) stu300_init_hw(dev); +	} + +	dev_err(&dev->pdev->dev, "giving up after %d attempts " +		"to reset the bus.\n",  BUSY_RELEASE_ATTEMPTS); + +	return -ETIMEDOUT; +} + +struct stu300_clkset { +	unsigned long rate; +	u32 setting; +}; + +static const struct stu300_clkset stu300_clktable[] = { +	{ 0, 0xFFU }, +	{ 2500000, I2C_OAR2_FR_25_10MHZ }, +	{ 10000000, I2C_OAR2_FR_10_1667MHZ }, +	{ 16670000, I2C_OAR2_FR_1667_2667MHZ }, +	{ 26670000, I2C_OAR2_FR_2667_40MHZ }, +	{ 40000000, I2C_OAR2_FR_40_5333MHZ }, +	{ 53330000, I2C_OAR2_FR_5333_66MHZ }, +	{ 66000000, I2C_OAR2_FR_66_80MHZ }, +	{ 80000000, I2C_OAR2_FR_80_100MHZ }, +	{ 100000000, 0xFFU }, +}; + +static int stu300_set_clk(struct stu300_dev *dev, unsigned long clkrate) +{ + +	u32 val; +	int i = 0; + +	/* Locate the apropriate clock setting */ +	while (i < ARRAY_SIZE(stu300_clktable) && +	       stu300_clktable[i].rate < clkrate) +		i++; + +	if (stu300_clktable[i].setting == 0xFFU) { +		dev_err(&dev->pdev->dev, "too %s clock rate requested " +			"(%lu Hz).\n", i ? "high" : "low", clkrate); +		return -EINVAL; +	} + +	stu300_wr8(stu300_clktable[i].setting, +		   dev->virtbase + I2C_OAR2); + +	dev_dbg(&dev->pdev->dev, "Clock rate %lu Hz, I2C bus speed %d Hz " +		"virtbase %p\n", clkrate, dev->speed, dev->virtbase); + +	if (dev->speed > 100000) +		/* Fast Mode I2C */ +		val = ((clkrate/dev->speed)-9)/3; +	else +		/* Standard Mode I2C */ +		val = ((clkrate/dev->speed)-7)/2; + +	/* According to spec the divider must be > 2 */ +	if (val < 0x002) { +		dev_err(&dev->pdev->dev, "too low clock rate (%lu Hz).\n", +			clkrate); +		return -EINVAL; +	} + +	/* We have 12 bits clock divider only! */ +	if (val & 0xFFFFF000U) { +		dev_err(&dev->pdev->dev, "too high clock rate (%lu Hz).\n", +			clkrate); +		return -EINVAL; +	} + +	if (dev->speed > 100000) { +		/* CC6..CC0 */ +		stu300_wr8((val & I2C_CCR_CC_MASK) | I2C_CCR_FMSM, +			   dev->virtbase + I2C_CCR); +		dev_dbg(&dev->pdev->dev, "set clock divider to 0x%08x, " +			"Fast Mode I2C\n", val); +	} else { +		/* CC6..CC0 */ +		stu300_wr8((val & I2C_CCR_CC_MASK), +			   dev->virtbase + I2C_CCR); +		dev_dbg(&dev->pdev->dev, "set clock divider to " +			"0x%08x, Standard Mode I2C\n", val); +	} + +	/* CC11..CC7 */ +	stu300_wr8(((val >> 7) & 0x1F), +		   dev->virtbase + I2C_ECCR); + +	return 0; +} + + +static int stu300_init_hw(struct stu300_dev *dev) +{ +	u32 dummy; +	unsigned long clkrate; +	int ret; + +	/* Disable controller */ +	stu300_wr8(0x00, dev->virtbase + I2C_CR); +	/* +	 * Set own address to some default value (0x00). +	 * We do not support slave mode anyway. +	 */ +	stu300_wr8(0x00, dev->virtbase + I2C_OAR1); +	/* +	 * The I2C controller only operates properly in 26 MHz but we +	 * program this driver as if we didn't know. This will also set the two +	 * high bits of the own address to zero as well. +	 * There is no known hardware issue with running in 13 MHz +	 * However, speeds over 200 kHz are not used. +	 */ +	clkrate = clk_get_rate(dev->clk); +	ret = stu300_set_clk(dev, clkrate); +	if (ret) +		return ret; +	/* +	 * Enable block, do it TWICE (hardware glitch) +	 * Setting bit 7 can enable DDC mode. (Not used currently.) +	 */ +	stu300_wr8(I2C_CR_PERIPHERAL_ENABLE, +				  dev->virtbase + I2C_CR); +	stu300_wr8(I2C_CR_PERIPHERAL_ENABLE, +				  dev->virtbase + I2C_CR); +	/* Make a dummy read of the status register SR1 & SR2 */ +	dummy = stu300_r8(dev->virtbase + I2C_SR2); +	dummy = stu300_r8(dev->virtbase + I2C_SR1); + +	return 0; +} + + + +/* Send slave address. */ +static int stu300_send_address(struct stu300_dev *dev, +				 struct i2c_msg *msg, int resend) +{ +	u32 val; +	int ret; + +	if (msg->flags & I2C_M_TEN) +		/* This is probably how 10 bit addresses look */ +		val = (0xf0 | (((u32) msg->addr & 0x300) >> 7)) & +			I2C_DR_D_MASK; +	else +		val = ((msg->addr << 1) & I2C_DR_D_MASK); + +	if (msg->flags & I2C_M_RD) { +		/* This is the direction bit */ +		val |= 0x01; +		if (resend) +			dev_dbg(&dev->pdev->dev, "read resend\n"); +	} else if (resend) +		dev_dbg(&dev->pdev->dev, "write resend\n"); +	stu300_wr8(val, dev->virtbase + I2C_DR); + +	/* For 10bit addressing, await 10bit request (EVENT 9) */ +	if (msg->flags & I2C_M_TEN) { +		ret = stu300_await_event(dev, STU300_EVENT_9); +		/* +		 * The slave device wants a 10bit address, send the rest +		 * of the bits (the LSBits) +		 */ +		val = msg->addr & I2C_DR_D_MASK; +		/* This clears "event 9" */ +		stu300_wr8(val, dev->virtbase + I2C_DR); +		if (ret != 0) +			return ret; +	} +	/* FIXME: Why no else here? two events for 10bit? +	 * Await event 6 (normal) or event 9 (10bit) +	 */ + +	if (resend) +		dev_dbg(&dev->pdev->dev, "await event 6\n"); +	ret = stu300_await_event(dev, STU300_EVENT_6); + +	/* +	 * Clear any pending EVENT 6 no matter what happend during +	 * await_event. +	 */ +	val = stu300_r8(dev->virtbase + I2C_CR); +	val |= I2C_CR_PERIPHERAL_ENABLE; +	stu300_wr8(val, dev->virtbase + I2C_CR); + +	return ret; +} + +static int stu300_xfer_msg(struct i2c_adapter *adap, +			     struct i2c_msg *msg, int stop) +{ +	u32 cr; +	u32 val; +	u32 i; +	int ret; +	int attempts = 0; +	struct stu300_dev *dev = i2c_get_adapdata(adap); + + +	clk_enable(dev->clk); + +	/* Remove this if (0) to trace each and every message. */ +	if (0) { +		dev_dbg(&dev->pdev->dev, "I2C message to: 0x%04x, len: %d, " +			"flags: 0x%04x, stop: %d\n", +			msg->addr, msg->len, msg->flags, stop); +	} + +	/* Zero-length messages are not supported by this hardware */ +	if (msg->len == 0) { +		ret = -EINVAL; +		goto exit_disable; +	} + +	/* +	 * For some reason, sending the address sometimes fails when running +	 * on  the 13 MHz clock. No interrupt arrives. This is a work around, +	 * which tries to restart and send the address up to 10 times before +	 * really giving up. Usually 5 to 8 attempts are enough. +	 */ +	do { +		if (attempts) +			dev_dbg(&dev->pdev->dev, "wait while busy\n"); +		/* Check that the bus is free, or wait until some timeout */ +		ret = stu300_wait_while_busy(dev); +		if (ret != 0) +			goto exit_disable; + +		if (attempts) +			dev_dbg(&dev->pdev->dev, "re-int hw\n"); +		/* +		 * According to ST, there is no problem if the clock is +		 * changed between 13 and 26 MHz during a transfer. +		 */ +		ret = stu300_init_hw(dev); +		if (ret) +			goto exit_disable; + +		/* Send a start condition */ +		cr = I2C_CR_PERIPHERAL_ENABLE; +		/* Setting the START bit puts the block in master mode */ +		if (!(msg->flags & I2C_M_NOSTART)) +			cr |= I2C_CR_START_ENABLE; +		if ((msg->flags & I2C_M_RD) && (msg->len > 1)) +			/* On read more than 1 byte, we need ack. */ +			cr |= I2C_CR_ACK_ENABLE; +		/* Check that it gets through */ +		if (!(msg->flags & I2C_M_NOSTART)) { +			if (attempts) +				dev_dbg(&dev->pdev->dev, "send start event\n"); +			ret = stu300_start_and_await_event(dev, cr, +							     STU300_EVENT_5); +		} + +		if (attempts) +			dev_dbg(&dev->pdev->dev, "send address\n"); + +		if (ret == 0) +			/* Send address */ +			ret = stu300_send_address(dev, msg, attempts != 0); + +		if (ret != 0) { +			attempts++; +			dev_dbg(&dev->pdev->dev, "failed sending address, " +				"retrying. Attempt: %d msg_index: %d/%d\n", +			       attempts, dev->msg_index, dev->msg_len); +		} + +	} while (ret != 0 && attempts < NUM_ADDR_RESEND_ATTEMPTS); + +	if (attempts < NUM_ADDR_RESEND_ATTEMPTS && attempts > 0) { +		dev_dbg(&dev->pdev->dev, "managed to get address " +		       "through after %d attempts\n", attempts); +	} else if (attempts == NUM_ADDR_RESEND_ATTEMPTS) { +		dev_dbg(&dev->pdev->dev, "I give up, tried %d times " +		       "to resend address.\n", +		       NUM_ADDR_RESEND_ATTEMPTS); +		goto exit_disable; +	} + +	if (msg->flags & I2C_M_RD) { +		/* READ: we read the actual bytes one at a time */ +		for (i = 0; i < msg->len; i++) { +			if (i == msg->len-1) { +				/* +				 * Disable ACK and set STOP condition before +				 * reading last byte +				 */ +				val = I2C_CR_PERIPHERAL_ENABLE; + +				if (stop) +					val |= I2C_CR_STOP_ENABLE; + +				stu300_wr8(val, +					   dev->virtbase + I2C_CR); +			} +			/* Wait for this byte... */ +			ret = stu300_await_event(dev, STU300_EVENT_7); +			if (ret != 0) +				goto exit_disable; +			/* This clears event 7 */ +			msg->buf[i] = (u8) stu300_r8(dev->virtbase + I2C_DR); +		} +	} else { +		/* WRITE: we send the actual bytes one at a time */ +		for (i = 0; i < msg->len; i++) { +			/* Write the byte */ +			stu300_wr8(msg->buf[i], +				   dev->virtbase + I2C_DR); +			/* Check status */ +			ret = stu300_await_event(dev, STU300_EVENT_8); +			/* Next write to DR will clear event 8 */ +			if (ret != 0) { +				dev_err(&dev->pdev->dev, "error awaiting " +				       "event 8 (%d)\n", ret); +				goto exit_disable; +			} +		} +		/* Check NAK */ +		if (!(msg->flags & I2C_M_IGNORE_NAK)) { +			if (stu300_r8(dev->virtbase + I2C_SR2) & +			    I2C_SR2_AF_IND) { +				dev_err(&dev->pdev->dev, "I2C payload " +				       "send returned NAK!\n"); +				ret = -EIO; +				goto exit_disable; +			} +		} +		if (stop) { +			/* Send stop condition */ +			val = I2C_CR_PERIPHERAL_ENABLE; +			val |= I2C_CR_STOP_ENABLE; +			stu300_wr8(val, dev->virtbase + I2C_CR); +		} +	} + +	/* Check that the bus is free, or wait until some timeout occurs */ +	ret = stu300_wait_while_busy(dev); +	if (ret != 0) { +		dev_err(&dev->pdev->dev, "timout waiting for transfer " +		       "to commence.\n"); +		goto exit_disable; +	} + +	/* Dummy read status registers */ +	val = stu300_r8(dev->virtbase + I2C_SR2); +	val = stu300_r8(dev->virtbase + I2C_SR1); +	ret = 0; + + exit_disable: +	/* Disable controller */ +	stu300_wr8(0x00, dev->virtbase + I2C_CR); +	clk_disable(dev->clk); +	return ret; +} + +static int stu300_xfer(struct i2c_adapter *adap, struct i2c_msg *msgs, +			 int num) +{ +	int ret = -1; +	int i; +	struct stu300_dev *dev = i2c_get_adapdata(adap); +	dev->msg_len = num; +	for (i = 0; i < num; i++) { +		/* +		 * Another driver appears to send stop for each message, +		 * here we only do that for the last message. Possibly some +		 * peripherals require this behaviour, then their drivers +		 * have to send single messages in order to get "stop" for +		 * each message. +		 */ +		dev->msg_index = i; + +		ret = stu300_xfer_msg(adap, &msgs[i], (i == (num - 1))); +		if (ret != 0) { +			num = ret; +			break; +		} +	} + +	return num; +} + +static u32 stu300_func(struct i2c_adapter *adap) +{ +	/* This is the simplest thing you can think of... */ +	return I2C_FUNC_I2C | I2C_FUNC_10BIT_ADDR; +} + +static const struct i2c_algorithm stu300_algo = { +	.master_xfer	= stu300_xfer, +	.functionality	= stu300_func, +}; + +static int __init +stu300_probe(struct platform_device *pdev) +{ +	struct stu300_dev *dev; +	struct i2c_adapter *adap; +	struct resource *res; +	int bus_nr; +	int ret = 0; + +	dev = kzalloc(sizeof(struct stu300_dev), GFP_KERNEL); +	if (!dev) { +		dev_err(&pdev->dev, "could not allocate device struct\n"); +		ret = -ENOMEM; +		goto err_no_devmem; +	} + +	bus_nr = pdev->id; +	dev->clk = clk_get(&pdev->dev, NULL); +	if (IS_ERR(dev->clk)) { +		ret = PTR_ERR(dev->clk); +		dev_err(&pdev->dev, "could not retrieve i2c bus clock\n"); +		goto err_no_clk; +	} + +	dev->pdev = pdev; +	platform_set_drvdata(pdev, dev); + +	res = platform_get_resource(pdev, IORESOURCE_MEM, 0); +	if (!res) { +		ret = -ENOENT; +		goto err_no_resource; +	} + +	dev->phybase = res->start; +	dev->physize = resource_size(res); + +	if (request_mem_region(dev->phybase, dev->physize, +			       NAME " I/O Area") == NULL) { +		ret = -EBUSY; +		goto err_no_ioregion; +	} + +	dev->virtbase = ioremap(dev->phybase, dev->physize); +	dev_dbg(&pdev->dev, "initialize bus device I2C%d on virtual " +		"base %p\n", bus_nr, dev->virtbase); +	if (!dev->virtbase) { +		ret = -ENOMEM; +		goto err_no_ioremap; +	} + +	dev->irq = platform_get_irq(pdev, 0); +	if (request_irq(dev->irq, stu300_irh, IRQF_DISABLED, +			NAME, dev)) { +		ret = -EIO; +		goto err_no_irq; +	} + +	dev->speed = scl_frequency; + +	clk_enable(dev->clk); +	ret = stu300_init_hw(dev); +	clk_disable(dev->clk); + +	if (ret != 0) { +		dev_err(&dev->pdev->dev, "error initializing hardware.\n"); +		goto err_init_hw; +	} + +	/* IRQ event handling initialization */ +	spin_lock_init(&dev->cmd_issue_lock); +	dev->cmd_event = STU300_EVENT_NONE; +	dev->cmd_err = STU300_ERROR_NONE; + +	adap = &dev->adapter; +	adap->owner = THIS_MODULE; +	/* DDC class but actually often used for more generic I2C */ +	adap->class = I2C_CLASS_DDC; +	strncpy(adap->name, "ST Microelectronics DDC I2C adapter", +		sizeof(adap->name)); +	adap->nr = bus_nr; +	adap->algo = &stu300_algo; +	adap->dev.parent = &pdev->dev; +	i2c_set_adapdata(adap, dev); + +	/* i2c device drivers may be active on return from add_adapter() */ +	ret = i2c_add_numbered_adapter(adap); +	if (ret) { +		dev_err(&dev->pdev->dev, "failure adding ST Micro DDC " +		       "I2C adapter\n"); +		goto err_add_adapter; +	} +	return 0; + + err_add_adapter: + err_init_hw: +	free_irq(dev->irq, dev); + err_no_irq: +	iounmap(dev->virtbase); + err_no_ioremap: +	release_mem_region(dev->phybase, dev->physize); + err_no_ioregion: +	platform_set_drvdata(pdev, NULL); + err_no_resource: +	clk_put(dev->clk); + err_no_clk: +	kfree(dev); + err_no_devmem: +	dev_err(&pdev->dev, "failed to add " NAME " adapter: %d\n", +		pdev->id); +	return ret; +} + +#ifdef CONFIG_PM +static int stu300_suspend(struct platform_device *pdev, pm_message_t state) +{ +	struct stu300_dev *dev = platform_get_drvdata(pdev); + +	/* Turn off everything */ +	stu300_wr8(0x00, dev->virtbase + I2C_CR); +	return 0; +} + +static int stu300_resume(struct platform_device *pdev) +{ +	int ret = 0; +	struct stu300_dev *dev = platform_get_drvdata(pdev); + +	clk_enable(dev->clk); +	ret = stu300_init_hw(dev); +	clk_disable(dev->clk); + +	if (ret != 0) +		dev_err(&pdev->dev, "error re-initializing hardware.\n"); +	return ret; +} +#else +#define stu300_suspend NULL +#define stu300_resume NULL +#endif + +static int __exit +stu300_remove(struct platform_device *pdev) +{ +	struct stu300_dev *dev = platform_get_drvdata(pdev); + +	i2c_del_adapter(&dev->adapter); +	/* Turn off everything */ +	stu300_wr8(0x00, dev->virtbase + I2C_CR); +	free_irq(dev->irq, dev); +	iounmap(dev->virtbase); +	release_mem_region(dev->phybase, dev->physize); +	clk_put(dev->clk); +	platform_set_drvdata(pdev, NULL); +	kfree(dev); +	return 0; +} + +static struct platform_driver stu300_i2c_driver = { +	.driver = { +		.name	= NAME, +		.owner	= THIS_MODULE, +	}, +	.remove		= __exit_p(stu300_remove), +	.suspend        = stu300_suspend, +	.resume         = stu300_resume, + +}; + +static int __init stu300_init(void) +{ +	return platform_driver_probe(&stu300_i2c_driver, stu300_probe); +} + +static void __exit stu300_exit(void) +{ +	platform_driver_unregister(&stu300_i2c_driver); +} + +/* + * The systems using this bus often have very basic devices such + * as regulators on the I2C bus, so this needs to be loaded early. + * Therefore it is registered in the subsys_initcall(). + */ +subsys_initcall(stu300_init); +module_exit(stu300_exit); + +MODULE_AUTHOR("Linus Walleij <linus.walleij@stericsson.com>"); +MODULE_DESCRIPTION("ST Micro DDC I2C adapter (" NAME ")"); +MODULE_LICENSE("GPL"); +MODULE_ALIAS("platform:" NAME); diff --git a/drivers/i2c/busses/i2c-versatile.c b/drivers/i2c/busses/i2c-versatile.c index fede619ba22..70de8216346 100644 --- a/drivers/i2c/busses/i2c-versatile.c +++ b/drivers/i2c/busses/i2c-versatile.c @@ -76,7 +76,7 @@ static int i2c_versatile_probe(struct platform_device *dev)  		goto err_out;  	} -	if (!request_mem_region(r->start, r->end - r->start + 1, "versatile-i2c")) { +	if (!request_mem_region(r->start, resource_size(r), "versatile-i2c")) {  		ret = -EBUSY;  		goto err_out;  	} @@ -87,7 +87,7 @@ static int i2c_versatile_probe(struct platform_device *dev)  		goto err_release;  	} -	i2c->base = ioremap(r->start, r->end - r->start + 1); +	i2c->base = ioremap(r->start, resource_size(r));  	if (!i2c->base) {  		ret = -ENOMEM;  		goto err_free; @@ -118,7 +118,7 @@ static int i2c_versatile_probe(struct platform_device *dev)   err_free:  	kfree(i2c);   err_release: -	release_mem_region(r->start, r->end - r->start + 1); +	release_mem_region(r->start, resource_size(r));   err_out:  	return ret;  } diff --git a/drivers/i2c/busses/i2c-viapro.c b/drivers/i2c/busses/i2c-viapro.c index 02e6f724b05..54d810a4d00 100644 --- a/drivers/i2c/busses/i2c-viapro.c +++ b/drivers/i2c/busses/i2c-viapro.c @@ -37,6 +37,7 @@     VT8251             0x3287             yes     CX700              0x8324             yes     VX800/VX820        0x8353             yes +   VX855/VX875        0x8409             yes     Note: we assume there can only be one device, with one SMBus interface.  */ @@ -404,6 +405,7 @@ found:  	switch (pdev->device) {  	case PCI_DEVICE_ID_VIA_CX700:  	case PCI_DEVICE_ID_VIA_VX800: +	case PCI_DEVICE_ID_VIA_VX855:  	case PCI_DEVICE_ID_VIA_8251:  	case PCI_DEVICE_ID_VIA_8237:  	case PCI_DEVICE_ID_VIA_8237A: @@ -469,6 +471,8 @@ static struct pci_device_id vt596_ids[] = {  	  .driver_data = SMBBA3 },  	{ PCI_DEVICE(PCI_VENDOR_ID_VIA, PCI_DEVICE_ID_VIA_VX800),  	  .driver_data = SMBBA3 }, +	{ PCI_DEVICE(PCI_VENDOR_ID_VIA, PCI_DEVICE_ID_VIA_VX855), +	  .driver_data = SMBBA3 },  	{ 0, }  }; diff --git a/drivers/i2c/busses/i2c-voodoo3.c b/drivers/i2c/busses/i2c-voodoo3.c index 1a474acc0dd..7663d57833a 100644 --- a/drivers/i2c/busses/i2c-voodoo3.c +++ b/drivers/i2c/busses/i2c-voodoo3.c @@ -163,7 +163,6 @@ static struct i2c_algo_bit_data voo_i2c_bit_data = {  static struct i2c_adapter voodoo3_i2c_adapter = {  	.owner		= THIS_MODULE, -	.class		= I2C_CLASS_TV_ANALOG,   	.name		= "I2C Voodoo3/Banshee adapter",  	.algo_data	= &voo_i2c_bit_data,  }; diff --git a/drivers/i2c/chips/Kconfig b/drivers/i2c/chips/Kconfig index 8f8c81eb0ae..02d746c9c47 100644 --- a/drivers/i2c/chips/Kconfig +++ b/drivers/i2c/chips/Kconfig @@ -64,21 +64,6 @@ config SENSORS_PCA9539  	  This driver is deprecated and will be dropped soon. Use  	  drivers/gpio/pca953x.c instead. -config SENSORS_MAX6875 -	tristate "Maxim MAX6875 Power supply supervisor" -	depends on EXPERIMENTAL -	help -	  If you say yes here you get support for the Maxim MAX6875 -	  EEPROM-programmable, quad power-supply sequencer/supervisor. - -	  This provides an interface to program the EEPROM and reset the chip. - -	  This driver also supports the Maxim MAX6874 hex power-supply -	  sequencer/supervisor if found at a compatible address. - -	  This driver can also be built as a module.  If so, the module -	  will be called max6875. -  config SENSORS_TSL2550  	tristate "Taos TSL2550 ambient light sensor"  	depends on EXPERIMENTAL diff --git a/drivers/i2c/chips/Makefile b/drivers/i2c/chips/Makefile index 55a37603718..f4680d16ee3 100644 --- a/drivers/i2c/chips/Makefile +++ b/drivers/i2c/chips/Makefile @@ -11,7 +11,6 @@  #  obj-$(CONFIG_DS1682)		+= ds1682.o -obj-$(CONFIG_SENSORS_MAX6875)	+= max6875.o  obj-$(CONFIG_SENSORS_PCA9539)	+= pca9539.o  obj-$(CONFIG_SENSORS_PCF8574)	+= pcf8574.o  obj-$(CONFIG_PCF8575)		+= pcf8575.o diff --git a/drivers/i2c/chips/max6875.c b/drivers/i2c/chips/max6875.c deleted file mode 100644 index 033d9d81ec8..00000000000 --- a/drivers/i2c/chips/max6875.c +++ /dev/null @@ -1,246 +0,0 @@ -/* -    max6875.c - driver for MAX6874/MAX6875 - -    Copyright (C) 2005 Ben Gardner <bgardner@wabtec.com> - -    Based on i2c/chips/eeprom.c - -    The MAX6875 has a bank of registers and two banks of EEPROM. -    Address ranges are defined as follows: -     * 0x0000 - 0x0046 = configuration registers -     * 0x8000 - 0x8046 = configuration EEPROM -     * 0x8100 - 0x82FF = user EEPROM - -    This driver makes the user EEPROM available for read. - -    The registers & config EEPROM should be accessed via i2c-dev. - -    The MAX6875 ignores the lowest address bit, so each chip responds to -    two addresses - 0x50/0x51 and 0x52/0x53. - -    Note that the MAX6875 uses i2c_smbus_write_byte_data() to set the read -    address, so this driver is destructive if loaded for the wrong EEPROM chip. - -    This program is free software; you can redistribute it and/or modify -    it under the terms of the GNU General Public License as published by -    the Free Software Foundation; version 2 of the License. -*/ - -#include <linux/kernel.h> -#include <linux/init.h> -#include <linux/module.h> -#include <linux/slab.h> -#include <linux/i2c.h> -#include <linux/mutex.h> - -/* Do not scan - the MAX6875 access method will write to some EEPROM chips */ -static const unsigned short normal_i2c[] = { I2C_CLIENT_END }; - -/* Insmod parameters */ -I2C_CLIENT_INSMOD_1(max6875); - -/* The MAX6875 can only read/write 16 bytes at a time */ -#define SLICE_SIZE			16 -#define SLICE_BITS			4 - -/* USER EEPROM is at addresses 0x8100 - 0x82FF */ -#define USER_EEPROM_BASE		0x8100 -#define USER_EEPROM_SIZE		0x0200 -#define USER_EEPROM_SLICES		32 - -/* MAX6875 commands */ -#define MAX6875_CMD_BLK_READ		0x84 - -/* Each client has this additional data */ -struct max6875_data { -	struct i2c_client	*fake_client; -	struct mutex		update_lock; - -	u32			valid; -	u8			data[USER_EEPROM_SIZE]; -	unsigned long		last_updated[USER_EEPROM_SLICES]; -}; - -static void max6875_update_slice(struct i2c_client *client, int slice) -{ -	struct max6875_data *data = i2c_get_clientdata(client); -	int i, j, addr; -	u8 *buf; - -	if (slice >= USER_EEPROM_SLICES) -		return; - -	mutex_lock(&data->update_lock); - -	buf = &data->data[slice << SLICE_BITS]; - -	if (!(data->valid & (1 << slice)) || -	    time_after(jiffies, data->last_updated[slice])) { - -		dev_dbg(&client->dev, "Starting update of slice %u\n", slice); - -		data->valid &= ~(1 << slice); - -		addr = USER_EEPROM_BASE + (slice << SLICE_BITS); - -		/* select the eeprom address */ -		if (i2c_smbus_write_byte_data(client, addr >> 8, addr & 0xFF)) { -			dev_err(&client->dev, "address set failed\n"); -			goto exit_up; -		} - -		if (i2c_check_functionality(client->adapter, -					    I2C_FUNC_SMBUS_READ_I2C_BLOCK)) { -			if (i2c_smbus_read_i2c_block_data(client, -							  MAX6875_CMD_BLK_READ, -							  SLICE_SIZE, -							  buf) != SLICE_SIZE) { -				goto exit_up; -			} -		} else { -			for (i = 0; i < SLICE_SIZE; i++) { -				j = i2c_smbus_read_byte(client); -				if (j < 0) { -					goto exit_up; -				} -				buf[i] = j; -			} -		} -		data->last_updated[slice] = jiffies; -		data->valid |= (1 << slice); -	} -exit_up: -	mutex_unlock(&data->update_lock); -} - -static ssize_t max6875_read(struct kobject *kobj, -			    struct bin_attribute *bin_attr, -			    char *buf, loff_t off, size_t count) -{ -	struct i2c_client *client = kobj_to_i2c_client(kobj); -	struct max6875_data *data = i2c_get_clientdata(client); -	int slice, max_slice; - -	if (off > USER_EEPROM_SIZE) -		return 0; - -	if (off + count > USER_EEPROM_SIZE) -		count = USER_EEPROM_SIZE - off; - -	/* refresh slices which contain requested bytes */ -	max_slice = (off + count - 1) >> SLICE_BITS; -	for (slice = (off >> SLICE_BITS); slice <= max_slice; slice++) -		max6875_update_slice(client, slice); - -	memcpy(buf, &data->data[off], count); - -	return count; -} - -static struct bin_attribute user_eeprom_attr = { -	.attr = { -		.name = "eeprom", -		.mode = S_IRUGO, -	}, -	.size = USER_EEPROM_SIZE, -	.read = max6875_read, -}; - -/* Return 0 if detection is successful, -ENODEV otherwise */ -static int max6875_detect(struct i2c_client *client, int kind, -			  struct i2c_board_info *info) -{ -	struct i2c_adapter *adapter = client->adapter; - -	if (!i2c_check_functionality(adapter, I2C_FUNC_SMBUS_WRITE_BYTE_DATA -				     | I2C_FUNC_SMBUS_READ_BYTE)) -		return -ENODEV; - -	/* Only check even addresses */ -	if (client->addr & 1) -		return -ENODEV; - -	strlcpy(info->type, "max6875", I2C_NAME_SIZE); - -	return 0; -} - -static int max6875_probe(struct i2c_client *client, -			 const struct i2c_device_id *id) -{ -	struct max6875_data *data; -	int err; - -	if (!(data = kzalloc(sizeof(struct max6875_data), GFP_KERNEL))) -		return -ENOMEM; - -	/* A fake client is created on the odd address */ -	data->fake_client = i2c_new_dummy(client->adapter, client->addr + 1); -	if (!data->fake_client) { -		err = -ENOMEM; -		goto exit_kfree; -	} - -	/* Init real i2c_client */ -	i2c_set_clientdata(client, data); -	mutex_init(&data->update_lock); - -	err = sysfs_create_bin_file(&client->dev.kobj, &user_eeprom_attr); -	if (err) -		goto exit_remove_fake; - -	return 0; - -exit_remove_fake: -	i2c_unregister_device(data->fake_client); -exit_kfree: -	kfree(data); -	return err; -} - -static int max6875_remove(struct i2c_client *client) -{ -	struct max6875_data *data = i2c_get_clientdata(client); - -	i2c_unregister_device(data->fake_client); - -	sysfs_remove_bin_file(&client->dev.kobj, &user_eeprom_attr); -	kfree(data); - -	return 0; -} - -static const struct i2c_device_id max6875_id[] = { -	{ "max6875", 0 }, -	{ } -}; - -static struct i2c_driver max6875_driver = { -	.driver = { -		.name	= "max6875", -	}, -	.probe		= max6875_probe, -	.remove		= max6875_remove, -	.id_table	= max6875_id, - -	.detect		= max6875_detect, -	.address_data	= &addr_data, -}; - -static int __init max6875_init(void) -{ -	return i2c_add_driver(&max6875_driver); -} - -static void __exit max6875_exit(void) -{ -	i2c_del_driver(&max6875_driver); -} - - -MODULE_AUTHOR("Ben Gardner <bgardner@wabtec.com>"); -MODULE_DESCRIPTION("MAX6875 driver"); -MODULE_LICENSE("GPL"); - -module_init(max6875_init); -module_exit(max6875_exit); diff --git a/drivers/i2c/i2c-boardinfo.c b/drivers/i2c/i2c-boardinfo.c index ffb35f09df0..a26a34a0664 100644 --- a/drivers/i2c/i2c-boardinfo.c +++ b/drivers/i2c/i2c-boardinfo.c @@ -18,6 +18,7 @@  #include <linux/kernel.h>  #include <linux/i2c.h> +#include <linux/rwsem.h>  #include "i2c-core.h" @@ -25,7 +26,7 @@  /* These symbols are exported ONLY FOR the i2c core.   * No other users will be supported.   */ -DEFINE_MUTEX(__i2c_board_lock); +DECLARE_RWSEM(__i2c_board_lock);  EXPORT_SYMBOL_GPL(__i2c_board_lock);  LIST_HEAD(__i2c_board_list); @@ -63,7 +64,7 @@ i2c_register_board_info(int busnum,  {  	int status; -	mutex_lock(&__i2c_board_lock); +	down_write(&__i2c_board_lock);  	/* dynamic bus numbers will be assigned after the last static one */  	if (busnum >= __i2c_first_dynamic_bus_num) @@ -84,7 +85,7 @@ i2c_register_board_info(int busnum,  		list_add_tail(&devinfo->list, &__i2c_board_list);  	} -	mutex_unlock(&__i2c_board_lock); +	up_write(&__i2c_board_lock);  	return status;  } diff --git a/drivers/i2c/i2c-core.c b/drivers/i2c/i2c-core.c index 85e2e919d1c..0e45c296d3d 100644 --- a/drivers/i2c/i2c-core.c +++ b/drivers/i2c/i2c-core.c @@ -29,21 +29,24 @@  #include <linux/i2c.h>  #include <linux/init.h>  #include <linux/idr.h> -#include <linux/platform_device.h>  #include <linux/mutex.h>  #include <linux/completion.h>  #include <linux/hardirq.h>  #include <linux/irqflags.h> +#include <linux/rwsem.h>  #include <asm/uaccess.h>  #include "i2c-core.h" +/* core_lock protects i2c_adapter_idr, userspace_devices, and guarantees +   that device detection, deletion of detected devices, and attach_adapter +   and detach_adapter calls are serialized */  static DEFINE_MUTEX(core_lock);  static DEFINE_IDR(i2c_adapter_idr); +static LIST_HEAD(userspace_devices); -#define is_newstyle_driver(d) ((d)->probe || (d)->remove || (d)->detect) - +static int i2c_check_addr(struct i2c_adapter *adapter, int addr);  static int i2c_detect(struct i2c_adapter *adapter, struct i2c_driver *driver);  /* ------------------------------------------------------------------------- */ @@ -64,12 +67,6 @@ static int i2c_device_match(struct device *dev, struct device_driver *drv)  	struct i2c_client	*client = to_i2c_client(dev);  	struct i2c_driver	*driver = to_i2c_driver(drv); -	/* make legacy i2c drivers bypass driver model probing entirely; -	 * such drivers scan each i2c adapter/bus themselves. -	 */ -	if (!is_newstyle_driver(driver)) -		return 0; -  	/* match on an id table if there is one */  	if (driver->id_table)  		return i2c_match_id(driver->id_table, client) != NULL; @@ -84,10 +81,6 @@ static int i2c_device_uevent(struct device *dev, struct kobj_uevent_env *env)  {  	struct i2c_client	*client = to_i2c_client(dev); -	/* by definition, legacy drivers can't hotplug */ -	if (dev->driver) -		return 0; -  	if (add_uevent_var(env, "MODALIAS=%s%s",  			   I2C_MODULE_PREFIX, client->name))  		return -ENOMEM; @@ -176,12 +169,6 @@ static int i2c_device_resume(struct device *dev)  	return driver->resume(to_i2c_client(dev));  } -static void i2c_client_release(struct device *dev) -{ -	struct i2c_client *client = to_i2c_client(dev); -	complete(&client->released); -} -  static void i2c_client_dev_release(struct device *dev)  {  	kfree(to_i2c_client(dev)); @@ -241,15 +228,17 @@ EXPORT_SYMBOL(i2c_verify_client);  /** - * i2c_new_device - instantiate an i2c device for use with a new style driver + * i2c_new_device - instantiate an i2c device   * @adap: the adapter managing the device   * @info: describes one I2C device; bus_num is ignored   * Context: can sleep   * - * Create a device to work with a new style i2c driver, where binding is - * handled through driver model probe()/remove() methods.  This call is not - * appropriate for use by mainboad initialization logic, which usually runs - * during an arch_initcall() long before any i2c_adapter could exist. + * Create an i2c device. Binding is handled through driver model + * probe()/remove() methods.  A driver may be bound to this device when we + * return from this function, or any later moment (e.g. maybe hotplugging will + * load the driver module).  This call is not appropriate for use by mainboard + * initialization logic, which usually runs during an arch_initcall() long + * before any i2c_adapter could exist.   *   * This returns the new i2c client, which may be saved for later use with   * i2c_unregister_device(); or NULL to indicate an error. @@ -277,17 +266,31 @@ i2c_new_device(struct i2c_adapter *adap, struct i2c_board_info const *info)  	strlcpy(client->name, info->type, sizeof(client->name)); -	/* a new style driver may be bound to this device when we -	 * return from this function, or any later moment (e.g. maybe -	 * hotplugging will load the driver module).  and the device -	 * refcount model is the standard driver model one. -	 */ -	status = i2c_attach_client(client); -	if (status < 0) { -		kfree(client); -		client = NULL; -	} +	/* Check for address business */ +	status = i2c_check_addr(adap, client->addr); +	if (status) +		goto out_err; + +	client->dev.parent = &client->adapter->dev; +	client->dev.bus = &i2c_bus_type; +	client->dev.release = i2c_client_dev_release; + +	dev_set_name(&client->dev, "%d-%04x", i2c_adapter_id(adap), +		     client->addr); +	status = device_register(&client->dev); +	if (status) +		goto out_err; + +	dev_dbg(&adap->dev, "client [%s] registered with bus id %s\n", +		client->name, dev_name(&client->dev)); +  	return client; + +out_err: +	dev_err(&adap->dev, "Failed to register i2c client %s at 0x%02x " +		"(%d)\n", client->name, client->addr, status); +	kfree(client); +	return NULL;  }  EXPORT_SYMBOL_GPL(i2c_new_device); @@ -299,28 +302,6 @@ EXPORT_SYMBOL_GPL(i2c_new_device);   */  void i2c_unregister_device(struct i2c_client *client)  { -	struct i2c_adapter	*adapter = client->adapter; -	struct i2c_driver	*driver = client->driver; - -	if (driver && !is_newstyle_driver(driver)) { -		dev_err(&client->dev, "can't unregister devices " -			"with legacy drivers\n"); -		WARN_ON(1); -		return; -	} - -	if (adapter->client_unregister) { -		if (adapter->client_unregister(client)) { -			dev_warn(&client->dev, -				 "client_unregister [%s] failed\n", -				 client->name); -		} -	} - -	mutex_lock(&adapter->clist_lock); -	list_del(&client->list); -	mutex_unlock(&adapter->clist_lock); -  	device_unregister(&client->dev);  }  EXPORT_SYMBOL_GPL(i2c_unregister_device); @@ -394,8 +375,128 @@ show_adapter_name(struct device *dev, struct device_attribute *attr, char *buf)  	return sprintf(buf, "%s\n", adap->name);  } +/* + * Let users instantiate I2C devices through sysfs. This can be used when + * platform initialization code doesn't contain the proper data for + * whatever reason. Also useful for drivers that do device detection and + * detection fails, either because the device uses an unexpected address, + * or this is a compatible device with different ID register values. + * + * Parameter checking may look overzealous, but we really don't want + * the user to provide incorrect parameters. + */ +static ssize_t +i2c_sysfs_new_device(struct device *dev, struct device_attribute *attr, +		     const char *buf, size_t count) +{ +	struct i2c_adapter *adap = to_i2c_adapter(dev); +	struct i2c_board_info info; +	struct i2c_client *client; +	char *blank, end; +	int res; + +	dev_warn(dev, "The new_device interface is still experimental " +		 "and may change in a near future\n"); +	memset(&info, 0, sizeof(struct i2c_board_info)); + +	blank = strchr(buf, ' '); +	if (!blank) { +		dev_err(dev, "%s: Missing parameters\n", "new_device"); +		return -EINVAL; +	} +	if (blank - buf > I2C_NAME_SIZE - 1) { +		dev_err(dev, "%s: Invalid device name\n", "new_device"); +		return -EINVAL; +	} +	memcpy(info.type, buf, blank - buf); + +	/* Parse remaining parameters, reject extra parameters */ +	res = sscanf(++blank, "%hi%c", &info.addr, &end); +	if (res < 1) { +		dev_err(dev, "%s: Can't parse I2C address\n", "new_device"); +		return -EINVAL; +	} +	if (res > 1  && end != '\n') { +		dev_err(dev, "%s: Extra parameters\n", "new_device"); +		return -EINVAL; +	} + +	if (info.addr < 0x03 || info.addr > 0x77) { +		dev_err(dev, "%s: Invalid I2C address 0x%hx\n", "new_device", +			info.addr); +		return -EINVAL; +	} + +	client = i2c_new_device(adap, &info); +	if (!client) +		return -EEXIST; + +	/* Keep track of the added device */ +	mutex_lock(&core_lock); +	list_add_tail(&client->detected, &userspace_devices); +	mutex_unlock(&core_lock); +	dev_info(dev, "%s: Instantiated device %s at 0x%02hx\n", "new_device", +		 info.type, info.addr); + +	return count; +} + +/* + * And of course let the users delete the devices they instantiated, if + * they got it wrong. This interface can only be used to delete devices + * instantiated by i2c_sysfs_new_device above. This guarantees that we + * don't delete devices to which some kernel code still has references. + * + * Parameter checking may look overzealous, but we really don't want + * the user to delete the wrong device. + */ +static ssize_t +i2c_sysfs_delete_device(struct device *dev, struct device_attribute *attr, +			const char *buf, size_t count) +{ +	struct i2c_adapter *adap = to_i2c_adapter(dev); +	struct i2c_client *client, *next; +	unsigned short addr; +	char end; +	int res; + +	/* Parse parameters, reject extra parameters */ +	res = sscanf(buf, "%hi%c", &addr, &end); +	if (res < 1) { +		dev_err(dev, "%s: Can't parse I2C address\n", "delete_device"); +		return -EINVAL; +	} +	if (res > 1  && end != '\n') { +		dev_err(dev, "%s: Extra parameters\n", "delete_device"); +		return -EINVAL; +	} + +	/* Make sure the device was added through sysfs */ +	res = -ENOENT; +	mutex_lock(&core_lock); +	list_for_each_entry_safe(client, next, &userspace_devices, detected) { +		if (client->addr == addr && client->adapter == adap) { +			dev_info(dev, "%s: Deleting device %s at 0x%02hx\n", +				 "delete_device", client->name, client->addr); + +			list_del(&client->detected); +			i2c_unregister_device(client); +			res = count; +			break; +		} +	} +	mutex_unlock(&core_lock); + +	if (res < 0) +		dev_err(dev, "%s: Can't find device in list\n", +			"delete_device"); +	return res; +} +  static struct device_attribute i2c_adapter_attrs[] = {  	__ATTR(name, S_IRUGO, show_adapter_name, NULL), +	__ATTR(new_device, S_IWUSR, NULL, i2c_sysfs_new_device), +	__ATTR(delete_device, S_IWUSR, NULL, i2c_sysfs_delete_device),  	{ },  }; @@ -409,7 +510,7 @@ static void i2c_scan_static_board_info(struct i2c_adapter *adapter)  {  	struct i2c_devinfo	*devinfo; -	mutex_lock(&__i2c_board_lock); +	down_read(&__i2c_board_lock);  	list_for_each_entry(devinfo, &__i2c_board_list, list) {  		if (devinfo->busnum == adapter->nr  				&& !i2c_new_device(adapter, @@ -418,7 +519,7 @@ static void i2c_scan_static_board_info(struct i2c_adapter *adapter)  				"Can't create device at 0x%02x\n",  				devinfo->board_info.addr);  	} -	mutex_unlock(&__i2c_board_lock); +	up_read(&__i2c_board_lock);  }  static int i2c_do_add_adapter(struct device_driver *d, void *data) @@ -442,24 +543,12 @@ static int i2c_register_adapter(struct i2c_adapter *adap)  	int res = 0, dummy;  	/* Can't register until after driver model init */ -	if (unlikely(WARN_ON(!i2c_bus_type.p))) -		return -EAGAIN; +	if (unlikely(WARN_ON(!i2c_bus_type.p))) { +		res = -EAGAIN; +		goto out_list; +	}  	mutex_init(&adap->bus_lock); -	mutex_init(&adap->clist_lock); -	INIT_LIST_HEAD(&adap->clients); - -	mutex_lock(&core_lock); - -	/* Add the adapter to the driver core. -	 * If the parent pointer is not set up, -	 * we add this adapter to the host bus. -	 */ -	if (adap->dev.parent == NULL) { -		adap->dev.parent = &platform_bus; -		pr_debug("I2C adapter driver [%s] forgot to specify " -			 "physical device\n", adap->name); -	}  	/* Set default timeout to 1 second if not already set */  	if (adap->timeout == 0) @@ -474,21 +563,23 @@ static int i2c_register_adapter(struct i2c_adapter *adap)  	dev_dbg(&adap->dev, "adapter [%s] registered\n", adap->name); -	/* create pre-declared device nodes for new-style drivers */ +	/* create pre-declared device nodes */  	if (adap->nr < __i2c_first_dynamic_bus_num)  		i2c_scan_static_board_info(adap);  	/* Notify drivers */ +	mutex_lock(&core_lock);  	dummy = bus_for_each_drv(&i2c_bus_type, NULL, adap,  				 i2c_do_add_adapter); - -out_unlock:  	mutex_unlock(&core_lock); -	return res; + +	return 0;  out_list: +	mutex_lock(&core_lock);  	idr_remove(&i2c_adapter_idr, adap->nr); -	goto out_unlock; +	mutex_unlock(&core_lock); +	return res;  }  /** @@ -607,6 +698,14 @@ static int i2c_do_del_adapter(struct device_driver *d, void *data)  	return res;  } +static int __unregister_client(struct device *dev, void *dummy) +{ +	struct i2c_client *client = i2c_verify_client(dev); +	if (client) +		i2c_unregister_device(client); +	return 0; +} +  /**   * i2c_del_adapter - unregister I2C adapter   * @adap: the adapter being unregistered @@ -617,46 +716,30 @@ static int i2c_do_del_adapter(struct device_driver *d, void *data)   */  int i2c_del_adapter(struct i2c_adapter *adap)  { -	struct i2c_client *client, *_n;  	int res = 0; - -	mutex_lock(&core_lock); +	struct i2c_adapter *found;  	/* First make sure that this adapter was ever added */ -	if (idr_find(&i2c_adapter_idr, adap->nr) != adap) { +	mutex_lock(&core_lock); +	found = idr_find(&i2c_adapter_idr, adap->nr); +	mutex_unlock(&core_lock); +	if (found != adap) {  		pr_debug("i2c-core: attempting to delete unregistered "  			 "adapter [%s]\n", adap->name); -		res = -EINVAL; -		goto out_unlock; +		return -EINVAL;  	}  	/* Tell drivers about this removal */ +	mutex_lock(&core_lock);  	res = bus_for_each_drv(&i2c_bus_type, NULL, adap,  			       i2c_do_del_adapter); +	mutex_unlock(&core_lock);  	if (res) -		goto out_unlock; - -	/* detach any active clients. This must be done first, because -	 * it can fail; in which case we give up. */ -	list_for_each_entry_safe_reverse(client, _n, &adap->clients, list) { -		struct i2c_driver	*driver; - -		driver = client->driver; - -		/* new style, follow standard driver model */ -		if (!driver || is_newstyle_driver(driver)) { -			i2c_unregister_device(client); -			continue; -		} +		return res; -		/* legacy drivers create and remove clients themselves */ -		if ((res = driver->detach_client(client))) { -			dev_err(&adap->dev, "detach_client failed for client " -				"[%s] at address 0x%02x\n", client->name, -				client->addr); -			goto out_unlock; -		} -	} +	/* Detach any active clients. This can't fail, thus we do not +	   checking the returned value. */ +	res = device_for_each_child(&adap->dev, NULL, __unregister_client);  	/* clean up the sysfs representation */  	init_completion(&adap->dev_released); @@ -666,7 +749,9 @@ int i2c_del_adapter(struct i2c_adapter *adap)  	wait_for_completion(&adap->dev_released);  	/* free bus id */ +	mutex_lock(&core_lock);  	idr_remove(&i2c_adapter_idr, adap->nr); +	mutex_unlock(&core_lock);  	dev_dbg(&adap->dev, "adapter [%s] unregistered\n", adap->name); @@ -674,9 +759,7 @@ int i2c_del_adapter(struct i2c_adapter *adap)  	   added again */  	memset(&adap->dev, 0, sizeof(adap->dev)); - out_unlock: -	mutex_unlock(&core_lock); -	return res; +	return 0;  }  EXPORT_SYMBOL(i2c_del_adapter); @@ -699,11 +782,7 @@ static int __attach_adapter(struct device *dev, void *data)  /*   * An i2c_driver is used with one or more i2c_client (device) nodes to access - * i2c slave chips, on a bus instance associated with some i2c_adapter.  There - * are two models for binding the driver to its device:  "new style" drivers - * follow the standard Linux driver model and just respond to probe() calls - * issued if the driver core sees they match(); "legacy" drivers create device - * nodes themselves. + * i2c slave chips, on a bus instance associated with some i2c_adapter.   */  int i2c_register_driver(struct module *owner, struct i2c_driver *driver) @@ -714,37 +793,26 @@ int i2c_register_driver(struct module *owner, struct i2c_driver *driver)  	if (unlikely(WARN_ON(!i2c_bus_type.p)))  		return -EAGAIN; -	/* new style driver methods can't mix with legacy ones */ -	if (is_newstyle_driver(driver)) { -		if (driver->detach_adapter || driver->detach_client) { -			printk(KERN_WARNING -					"i2c-core: driver [%s] is confused\n", -					driver->driver.name); -			return -EINVAL; -		} -	} -  	/* add the driver to the list of i2c drivers in the driver core */  	driver->driver.owner = owner;  	driver->driver.bus = &i2c_bus_type; -	/* for new style drivers, when registration returns the driver core +	/* When registration returns, the driver core  	 * will have called probe() for all matching-but-unbound devices.  	 */  	res = driver_register(&driver->driver);  	if (res)  		return res; -	mutex_lock(&core_lock); -  	pr_debug("i2c-core: driver [%s] registered\n", driver->driver.name);  	INIT_LIST_HEAD(&driver->clients);  	/* Walk the adapters that are already present */ +	mutex_lock(&core_lock);  	class_for_each_device(&i2c_adapter_class, NULL, driver,  			      __attach_adapter); -  	mutex_unlock(&core_lock); +  	return 0;  }  EXPORT_SYMBOL(i2c_register_driver); @@ -764,32 +832,11 @@ static int __detach_adapter(struct device *dev, void *data)  		i2c_unregister_device(client);  	} -	if (is_newstyle_driver(driver)) -		return 0; - -	/* Have a look at each adapter, if clients of this driver are still -	 * attached. If so, detach them to be able to kill the driver -	 * afterwards. -	 */  	if (driver->detach_adapter) {  		if (driver->detach_adapter(adapter))  			dev_err(&adapter->dev,  				"detach_adapter failed for driver [%s]\n",  				driver->driver.name); -	} else { -		struct i2c_client *client, *_n; - -		list_for_each_entry_safe(client, _n, &adapter->clients, list) { -			if (client->driver != driver) -				continue; -			dev_dbg(&adapter->dev, -				"detaching client [%s] at 0x%02x\n", -				client->name, client->addr); -			if (driver->detach_client(client)) -				dev_err(&adapter->dev, "detach_client " -					"failed for client [%s] at 0x%02x\n", -					client->name, client->addr); -		}  	}  	return 0; @@ -803,14 +850,12 @@ static int __detach_adapter(struct device *dev, void *data)  void i2c_del_driver(struct i2c_driver *driver)  {  	mutex_lock(&core_lock); -  	class_for_each_device(&i2c_adapter_class, NULL, driver,  			      __detach_adapter); +	mutex_unlock(&core_lock);  	driver_unregister(&driver->driver);  	pr_debug("i2c-core: driver [%s] unregistered\n", driver->driver.name); - -	mutex_unlock(&core_lock);  }  EXPORT_SYMBOL(i2c_del_driver); @@ -831,86 +876,6 @@ static int i2c_check_addr(struct i2c_adapter *adapter, int addr)  	return device_for_each_child(&adapter->dev, &addr, __i2c_check_addr);  } -int i2c_attach_client(struct i2c_client *client) -{ -	struct i2c_adapter *adapter = client->adapter; -	int res; - -	/* Check for address business */ -	res = i2c_check_addr(adapter, client->addr); -	if (res) -		return res; - -	client->dev.parent = &client->adapter->dev; -	client->dev.bus = &i2c_bus_type; - -	if (client->driver) -		client->dev.driver = &client->driver->driver; - -	if (client->driver && !is_newstyle_driver(client->driver)) { -		client->dev.release = i2c_client_release; -		dev_set_uevent_suppress(&client->dev, 1); -	} else -		client->dev.release = i2c_client_dev_release; - -	dev_set_name(&client->dev, "%d-%04x", i2c_adapter_id(adapter), -		     client->addr); -	res = device_register(&client->dev); -	if (res) -		goto out_err; - -	mutex_lock(&adapter->clist_lock); -	list_add_tail(&client->list, &adapter->clients); -	mutex_unlock(&adapter->clist_lock); - -	dev_dbg(&adapter->dev, "client [%s] registered with bus id %s\n", -		client->name, dev_name(&client->dev)); - -	if (adapter->client_register)  { -		if (adapter->client_register(client)) { -			dev_dbg(&adapter->dev, "client_register " -				"failed for client [%s] at 0x%02x\n", -				client->name, client->addr); -		} -	} - -	return 0; - -out_err: -	dev_err(&adapter->dev, "Failed to attach i2c client %s at 0x%02x " -		"(%d)\n", client->name, client->addr, res); -	return res; -} -EXPORT_SYMBOL(i2c_attach_client); - -int i2c_detach_client(struct i2c_client *client) -{ -	struct i2c_adapter *adapter = client->adapter; -	int res = 0; - -	if (adapter->client_unregister)  { -		res = adapter->client_unregister(client); -		if (res) { -			dev_err(&client->dev, -				"client_unregister [%s] failed, " -				"client not detached\n", client->name); -			goto out; -		} -	} - -	mutex_lock(&adapter->clist_lock); -	list_del(&client->list); -	mutex_unlock(&adapter->clist_lock); - -	init_completion(&client->released); -	device_unregister(&client->dev); -	wait_for_completion(&client->released); - - out: -	return res; -} -EXPORT_SYMBOL(i2c_detach_client); -  /**   * i2c_use_client - increments the reference count of the i2c client structure   * @client: the client being referenced @@ -1022,7 +987,8 @@ module_exit(i2c_exit);   */  int i2c_transfer(struct i2c_adapter *adap, struct i2c_msg *msgs, int num)  { -	int ret; +	unsigned long orig_jiffies; +	int ret, try;  	/* REVISIT the fault reporting model here is weak:  	 * @@ -1060,7 +1026,15 @@ int i2c_transfer(struct i2c_adapter *adap, struct i2c_msg *msgs, int num)  			mutex_lock_nested(&adap->bus_lock, adap->level);  		} -		ret = adap->algo->master_xfer(adap,msgs,num); +		/* Retry automatically on arbitration loss */ +		orig_jiffies = jiffies; +		for (ret = 0, try = 0; try <= adap->retries; try++) { +			ret = adap->algo->master_xfer(adap, msgs, num); +			if (ret != -EAGAIN) +				break; +			if (time_after(jiffies, orig_jiffies + adap->timeout)) +				break; +		}  		mutex_unlock(&adap->bus_lock);  		return ret; @@ -1131,144 +1105,7 @@ EXPORT_SYMBOL(i2c_master_recv);   * Will not work for 10-bit addresses!   * ----------------------------------------------------   */ -static int i2c_probe_address(struct i2c_adapter *adapter, int addr, int kind, -			     int (*found_proc) (struct i2c_adapter *, int, int)) -{ -	int err; - -	/* Make sure the address is valid */ -	if (addr < 0x03 || addr > 0x77) { -		dev_warn(&adapter->dev, "Invalid probe address 0x%02x\n", -			 addr); -		return -EINVAL; -	} - -	/* Skip if already in use */ -	if (i2c_check_addr(adapter, addr)) -		return 0; - -	/* Make sure there is something at this address, unless forced */ -	if (kind < 0) { -		if (i2c_smbus_xfer(adapter, addr, 0, 0, 0, -				   I2C_SMBUS_QUICK, NULL) < 0) -			return 0; - -		/* prevent 24RF08 corruption */ -		if ((addr & ~0x0f) == 0x50) -			i2c_smbus_xfer(adapter, addr, 0, 0, 0, -				       I2C_SMBUS_QUICK, NULL); -	} - -	/* Finally call the custom detection function */ -	err = found_proc(adapter, addr, kind); -	/* -ENODEV can be returned if there is a chip at the given address -	   but it isn't supported by this chip driver. We catch it here as -	   this isn't an error. */ -	if (err == -ENODEV) -		err = 0; - -	if (err) -		dev_warn(&adapter->dev, "Client creation failed at 0x%x (%d)\n", -			 addr, err); -	return err; -} - -int i2c_probe(struct i2c_adapter *adapter, -	      const struct i2c_client_address_data *address_data, -	      int (*found_proc) (struct i2c_adapter *, int, int)) -{ -	int i, err; -	int adap_id = i2c_adapter_id(adapter); -	/* Force entries are done first, and are not affected by ignore -	   entries */ -	if (address_data->forces) { -		const unsigned short * const *forces = address_data->forces; -		int kind; - -		for (kind = 0; forces[kind]; kind++) { -			for (i = 0; forces[kind][i] != I2C_CLIENT_END; -			     i += 2) { -				if (forces[kind][i] == adap_id -				 || forces[kind][i] == ANY_I2C_BUS) { -					dev_dbg(&adapter->dev, "found force " -						"parameter for adapter %d, " -						"addr 0x%02x, kind %d\n", -						adap_id, forces[kind][i + 1], -						kind); -					err = i2c_probe_address(adapter, -						forces[kind][i + 1], -						kind, found_proc); -					if (err) -						return err; -				} -			} -		} -	} - -	/* Stop here if we can't use SMBUS_QUICK */ -	if (!i2c_check_functionality(adapter, I2C_FUNC_SMBUS_QUICK)) { -		if (address_data->probe[0] == I2C_CLIENT_END -		 && address_data->normal_i2c[0] == I2C_CLIENT_END) -			return 0; - -		dev_dbg(&adapter->dev, "SMBus Quick command not supported, " -			"can't probe for chips\n"); -		return -EOPNOTSUPP; -	} - -	/* Probe entries are done second, and are not affected by ignore -	   entries either */ -	for (i = 0; address_data->probe[i] != I2C_CLIENT_END; i += 2) { -		if (address_data->probe[i] == adap_id -		 || address_data->probe[i] == ANY_I2C_BUS) { -			dev_dbg(&adapter->dev, "found probe parameter for " -				"adapter %d, addr 0x%02x\n", adap_id, -				address_data->probe[i + 1]); -			err = i2c_probe_address(adapter, -						address_data->probe[i + 1], -						-1, found_proc); -			if (err) -				return err; -		} -	} - -	/* Normal entries are done last, unless shadowed by an ignore entry */ -	for (i = 0; address_data->normal_i2c[i] != I2C_CLIENT_END; i += 1) { -		int j, ignore; - -		ignore = 0; -		for (j = 0; address_data->ignore[j] != I2C_CLIENT_END; -		     j += 2) { -			if ((address_data->ignore[j] == adap_id || -			     address_data->ignore[j] == ANY_I2C_BUS) -			 && address_data->ignore[j + 1] -			    == address_data->normal_i2c[i]) { -				dev_dbg(&adapter->dev, "found ignore " -					"parameter for adapter %d, " -					"addr 0x%02x\n", adap_id, -					address_data->ignore[j + 1]); -				ignore = 1; -				break; -			} -		} -		if (ignore) -			continue; - -		dev_dbg(&adapter->dev, "found normal entry for adapter %d, " -			"addr 0x%02x\n", adap_id, -			address_data->normal_i2c[i]); -		err = i2c_probe_address(adapter, address_data->normal_i2c[i], -					-1, found_proc); -		if (err) -			return err; -	} - -	return 0; -} -EXPORT_SYMBOL(i2c_probe); - -/* Separate detection function for new-style drivers */  static int i2c_detect_address(struct i2c_client *temp_client, int kind,  			      struct i2c_driver *driver)  { @@ -1509,7 +1346,7 @@ struct i2c_adapter* i2c_get_adapter(int id)  	struct i2c_adapter *adapter;  	mutex_lock(&core_lock); -	adapter = (struct i2c_adapter *)idr_find(&i2c_adapter_idr, id); +	adapter = idr_find(&i2c_adapter_idr, id);  	if (adapter && !try_module_get(adapter->owner))  		adapter = NULL; @@ -1995,14 +1832,27 @@ s32 i2c_smbus_xfer(struct i2c_adapter *adapter, u16 addr, unsigned short flags,  		   char read_write, u8 command, int protocol,  		   union i2c_smbus_data *data)  { +	unsigned long orig_jiffies; +	int try;  	s32 res;  	flags &= I2C_M_TEN | I2C_CLIENT_PEC;  	if (adapter->algo->smbus_xfer) {  		mutex_lock(&adapter->bus_lock); -		res = adapter->algo->smbus_xfer(adapter,addr,flags,read_write, -						command, protocol, data); + +		/* Retry automatically on arbitration loss */ +		orig_jiffies = jiffies; +		for (res = 0, try = 0; try <= adapter->retries; try++) { +			res = adapter->algo->smbus_xfer(adapter, addr, flags, +							read_write, command, +							protocol, data); +			if (res != -EAGAIN) +				break; +			if (time_after(jiffies, +				       orig_jiffies + adapter->timeout)) +				break; +		}  		mutex_unlock(&adapter->bus_lock);  	} else  		res = i2c_smbus_xfer_emulated(adapter,addr,flags,read_write, diff --git a/drivers/i2c/i2c-core.h b/drivers/i2c/i2c-core.h index cd5bff87485..9f9c57ff670 100644 --- a/drivers/i2c/i2c-core.h +++ b/drivers/i2c/i2c-core.h @@ -16,6 +16,8 @@   * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.   */ +#include <linux/rwsem.h> +  struct i2c_devinfo {  	struct list_head	list;  	int			busnum; @@ -25,7 +27,7 @@ struct i2c_devinfo {  /* board_lock protects board_list and first_dynamic_bus_num.   * only i2c core components are allowed to use these symbols.   */ -extern struct mutex	__i2c_board_lock; +extern struct rw_semaphore	__i2c_board_lock;  extern struct list_head	__i2c_board_list;  extern int		__i2c_first_dynamic_bus_num; | 
