diff options
| -rw-r--r-- | drivers/i2c/busses/i2c-nomadik.c | 36 | 
1 files changed, 21 insertions, 15 deletions
| diff --git a/drivers/i2c/busses/i2c-nomadik.c b/drivers/i2c/busses/i2c-nomadik.c index 73de8ade10b1..c9fffd0389fe 100644 --- a/drivers/i2c/busses/i2c-nomadik.c +++ b/drivers/i2c/busses/i2c-nomadik.c | |||
| @@ -1,5 +1,5 @@ | |||
| 1 | /* | 1 | /* | 
| 2 | * Copyright (C) 2009 ST-Ericsson | 2 | * Copyright (C) 2009 ST-Ericsson SA | 
| 3 | * Copyright (C) 2009 STMicroelectronics | 3 | * Copyright (C) 2009 STMicroelectronics | 
| 4 | * | 4 | * | 
| 5 | * I2C master mode controller driver, used in Nomadik 8815 | 5 | * I2C master mode controller driver, used in Nomadik 8815 | 
| @@ -103,6 +103,9 @@ | |||
| 103 | /* maximum threshold value */ | 103 | /* maximum threshold value */ | 
| 104 | #define MAX_I2C_FIFO_THRESHOLD 15 | 104 | #define MAX_I2C_FIFO_THRESHOLD 15 | 
| 105 | 105 | ||
| 106 | /* per-transfer delay, required for the hardware to stabilize */ | ||
| 107 | #define I2C_DELAY 150 | ||
| 108 | |||
| 106 | enum i2c_status { | 109 | enum i2c_status { | 
| 107 | I2C_NOP, | 110 | I2C_NOP, | 
| 108 | I2C_ON_GOING, | 111 | I2C_ON_GOING, | 
| @@ -118,7 +121,7 @@ enum i2c_operation { | |||
| 118 | }; | 121 | }; | 
| 119 | 122 | ||
| 120 | /* controller response timeout in ms */ | 123 | /* controller response timeout in ms */ | 
| 121 | #define I2C_TIMEOUT_MS 500 | 124 | #define I2C_TIMEOUT_MS 2000 | 
| 122 | 125 | ||
| 123 | /** | 126 | /** | 
| 124 | * struct i2c_nmk_client - client specific data | 127 | * struct i2c_nmk_client - client specific data | 
| @@ -250,6 +253,8 @@ static int init_hw(struct nmk_i2c_dev *dev) | |||
| 250 | { | 253 | { | 
| 251 | int stat; | 254 | int stat; | 
| 252 | 255 | ||
| 256 | clk_enable(dev->clk); | ||
| 257 | |||
| 253 | stat = flush_i2c_fifo(dev); | 258 | stat = flush_i2c_fifo(dev); | 
| 254 | if (stat) | 259 | if (stat) | 
| 255 | return stat; | 260 | return stat; | 
| @@ -263,6 +268,9 @@ static int init_hw(struct nmk_i2c_dev *dev) | |||
| 263 | 268 | ||
| 264 | dev->cli.operation = I2C_NO_OPERATION; | 269 | dev->cli.operation = I2C_NO_OPERATION; | 
| 265 | 270 | ||
| 271 | clk_disable(dev->clk); | ||
| 272 | |||
| 273 | udelay(I2C_DELAY); | ||
| 266 | return 0; | 274 | return 0; | 
| 267 | } | 275 | } | 
| 268 | 276 | ||
| @@ -431,7 +439,6 @@ static int read_i2c(struct nmk_i2c_dev *dev) | |||
| 431 | (void) init_hw(dev); | 439 | (void) init_hw(dev); | 
| 432 | status = -ETIMEDOUT; | 440 | status = -ETIMEDOUT; | 
| 433 | } | 441 | } | 
| 434 | |||
| 435 | return status; | 442 | return status; | 
| 436 | } | 443 | } | 
| 437 | 444 | ||
| @@ -502,9 +509,9 @@ static int write_i2c(struct nmk_i2c_dev *dev) | |||
| 502 | 509 | ||
| 503 | /** | 510 | /** | 
| 504 | * nmk_i2c_xfer() - I2C transfer function used by kernel framework | 511 | * nmk_i2c_xfer() - I2C transfer function used by kernel framework | 
| 505 | * @i2c_adap - Adapter pointer to the controller | 512 | * @i2c_adap: Adapter pointer to the controller | 
| 506 | * @msgs[] - Pointer to data to be written. | 513 | * @msgs: Pointer to data to be written. | 
| 507 | * @num_msgs - Number of messages to be executed | 514 | * @num_msgs: Number of messages to be executed | 
| 508 | * | 515 | * | 
| 509 | * This is the function called by the generic kernel i2c_transfer() | 516 | * This is the function called by the generic kernel i2c_transfer() | 
| 510 | * or i2c_smbus...() API calls. Note that this code is protected by the | 517 | * or i2c_smbus...() API calls. Note that this code is protected by the | 
| @@ -559,6 +566,8 @@ static int nmk_i2c_xfer(struct i2c_adapter *i2c_adap, | |||
| 559 | if (status) | 566 | if (status) | 
| 560 | return status; | 567 | return status; | 
| 561 | 568 | ||
| 569 | clk_enable(dev->clk); | ||
| 570 | |||
| 562 | /* setup the i2c controller */ | 571 | /* setup the i2c controller */ | 
| 563 | setup_i2c_controller(dev); | 572 | setup_i2c_controller(dev); | 
| 564 | 573 | ||
| @@ -591,10 +600,13 @@ static int nmk_i2c_xfer(struct i2c_adapter *i2c_adap, | |||
| 591 | dev_err(&dev->pdev->dev, "%s\n", | 600 | dev_err(&dev->pdev->dev, "%s\n", | 
| 592 | cause >= ARRAY_SIZE(abort_causes) | 601 | cause >= ARRAY_SIZE(abort_causes) | 
| 593 | ? "unknown reason" : abort_causes[cause]); | 602 | ? "unknown reason" : abort_causes[cause]); | 
| 603 | clk_disable(dev->clk); | ||
| 594 | return status; | 604 | return status; | 
| 595 | } | 605 | } | 
| 596 | mdelay(1); | 606 | udelay(I2C_DELAY); | 
| 597 | } | 607 | } | 
| 608 | clk_disable(dev->clk); | ||
| 609 | |||
| 598 | /* return the no. messages processed */ | 610 | /* return the no. messages processed */ | 
| 599 | if (status) | 611 | if (status) | 
| 600 | return status; | 612 | return status; | 
| @@ -605,6 +617,7 @@ static int nmk_i2c_xfer(struct i2c_adapter *i2c_adap, | |||
| 605 | /** | 617 | /** | 
| 606 | * disable_interrupts() - disable the interrupts | 618 | * disable_interrupts() - disable the interrupts | 
| 607 | * @dev: private data of controller | 619 | * @dev: private data of controller | 
| 620 | * @irq: interrupt number | ||
| 608 | */ | 621 | */ | 
| 609 | static int disable_interrupts(struct nmk_i2c_dev *dev, u32 irq) | 622 | static int disable_interrupts(struct nmk_i2c_dev *dev, u32 irq) | 
| 610 | { | 623 | { | 
| @@ -794,10 +807,7 @@ static irqreturn_t i2c_irq_handler(int irq, void *arg) | |||
| 794 | 807 | ||
| 795 | static unsigned int nmk_i2c_functionality(struct i2c_adapter *adap) | 808 | static unsigned int nmk_i2c_functionality(struct i2c_adapter *adap) | 
| 796 | { | 809 | { | 
| 797 | return I2C_FUNC_I2C | 810 | return I2C_FUNC_I2C | I2C_FUNC_SMBUS_EMUL; | 
| 798 | | I2C_FUNC_SMBUS_BYTE_DATA | ||
| 799 | | I2C_FUNC_SMBUS_WORD_DATA | ||
| 800 | | I2C_FUNC_SMBUS_I2C_BLOCK; | ||
| 801 | } | 811 | } | 
| 802 | 812 | ||
| 803 | static const struct i2c_algorithm nmk_i2c_algo = { | 813 | static const struct i2c_algorithm nmk_i2c_algo = { | 
| @@ -857,8 +867,6 @@ static int __devinit nmk_i2c_probe(struct platform_device *pdev) | |||
| 857 | goto err_no_clk; | 867 | goto err_no_clk; | 
| 858 | } | 868 | } | 
| 859 | 869 | ||
| 860 | clk_enable(dev->clk); | ||
| 861 | |||
| 862 | adap = &dev->adap; | 870 | adap = &dev->adap; | 
| 863 | adap->dev.parent = &pdev->dev; | 871 | adap->dev.parent = &pdev->dev; | 
| 864 | adap->owner = THIS_MODULE; | 872 | adap->owner = THIS_MODULE; | 
| @@ -895,7 +903,6 @@ static int __devinit nmk_i2c_probe(struct platform_device *pdev) | |||
| 895 | return 0; | 903 | return 0; | 
| 896 | 904 | ||
| 897 | err_init_hw: | 905 | err_init_hw: | 
| 898 | clk_disable(dev->clk); | ||
| 899 | err_add_adap: | 906 | err_add_adap: | 
| 900 | clk_put(dev->clk); | 907 | clk_put(dev->clk); | 
| 901 | err_no_clk: | 908 | err_no_clk: | 
| @@ -928,7 +935,6 @@ static int __devexit nmk_i2c_remove(struct platform_device *pdev) | |||
| 928 | iounmap(dev->virtbase); | 935 | iounmap(dev->virtbase); | 
| 929 | if (res) | 936 | if (res) | 
| 930 | release_mem_region(res->start, resource_size(res)); | 937 | release_mem_region(res->start, resource_size(res)); | 
| 931 | clk_disable(dev->clk); | ||
| 932 | clk_put(dev->clk); | 938 | clk_put(dev->clk); | 
| 933 | platform_set_drvdata(pdev, NULL); | 939 | platform_set_drvdata(pdev, NULL); | 
| 934 | kfree(dev); | 940 | kfree(dev); | 
