.. | .. |
---|
43 | 43 | #include <linux/module.h> |
---|
44 | 44 | #include <linux/of.h> |
---|
45 | 45 | #include <linux/platform_device.h> |
---|
| 46 | +#include <linux/pm_runtime.h> |
---|
46 | 47 | |
---|
47 | 48 | #define RIIC_ICCR1 0x00 |
---|
48 | 49 | #define RIIC_ICCR2 0x04 |
---|
.. | .. |
---|
112 | 113 | { |
---|
113 | 114 | struct riic_dev *riic = i2c_get_adapdata(adap); |
---|
114 | 115 | unsigned long time_left; |
---|
115 | | - int i, ret; |
---|
| 116 | + int i; |
---|
116 | 117 | u8 start_bit; |
---|
117 | 118 | |
---|
118 | | - ret = clk_prepare_enable(riic->clk); |
---|
119 | | - if (ret) |
---|
120 | | - return ret; |
---|
| 119 | + pm_runtime_get_sync(adap->dev.parent); |
---|
121 | 120 | |
---|
122 | 121 | if (readb(riic->base + RIIC_ICCR2) & ICCR2_BBSY) { |
---|
123 | 122 | riic->err = -EBUSY; |
---|
.. | .. |
---|
150 | 149 | } |
---|
151 | 150 | |
---|
152 | 151 | out: |
---|
153 | | - clk_disable_unprepare(riic->clk); |
---|
| 152 | + pm_runtime_put(adap->dev.parent); |
---|
154 | 153 | |
---|
155 | 154 | return riic->err ?: num; |
---|
156 | 155 | } |
---|
.. | .. |
---|
282 | 281 | |
---|
283 | 282 | static int riic_init_hw(struct riic_dev *riic, struct i2c_timings *t) |
---|
284 | 283 | { |
---|
285 | | - int ret; |
---|
| 284 | + int ret = 0; |
---|
286 | 285 | unsigned long rate; |
---|
287 | 286 | int total_ticks, cks, brl, brh; |
---|
288 | 287 | |
---|
289 | | - ret = clk_prepare_enable(riic->clk); |
---|
290 | | - if (ret) |
---|
291 | | - return ret; |
---|
| 288 | + pm_runtime_get_sync(riic->adapter.dev.parent); |
---|
292 | 289 | |
---|
293 | | - if (t->bus_freq_hz > 400000) { |
---|
| 290 | + if (t->bus_freq_hz > I2C_MAX_FAST_MODE_FREQ) { |
---|
294 | 291 | dev_err(&riic->adapter.dev, |
---|
295 | | - "unsupported bus speed (%dHz). 400000 max\n", |
---|
296 | | - t->bus_freq_hz); |
---|
297 | | - clk_disable_unprepare(riic->clk); |
---|
298 | | - return -EINVAL; |
---|
| 292 | + "unsupported bus speed (%dHz). %d max\n", |
---|
| 293 | + t->bus_freq_hz, I2C_MAX_FAST_MODE_FREQ); |
---|
| 294 | + ret = -EINVAL; |
---|
| 295 | + goto out; |
---|
299 | 296 | } |
---|
300 | 297 | |
---|
301 | 298 | rate = clk_get_rate(riic->clk); |
---|
.. | .. |
---|
333 | 330 | if (brl > (0x1F + 3)) { |
---|
334 | 331 | dev_err(&riic->adapter.dev, "invalid speed (%lu). Too slow.\n", |
---|
335 | 332 | (unsigned long)t->bus_freq_hz); |
---|
336 | | - clk_disable_unprepare(riic->clk); |
---|
337 | | - return -EINVAL; |
---|
| 333 | + ret = -EINVAL; |
---|
| 334 | + goto out; |
---|
338 | 335 | } |
---|
339 | 336 | |
---|
340 | 337 | brh = total_ticks - brl; |
---|
.. | .. |
---|
379 | 376 | |
---|
380 | 377 | riic_clear_set_bit(riic, ICCR1_IICRST, 0, RIIC_ICCR1); |
---|
381 | 378 | |
---|
382 | | - clk_disable_unprepare(riic->clk); |
---|
383 | | - |
---|
384 | | - return 0; |
---|
| 379 | +out: |
---|
| 380 | + pm_runtime_put(riic->adapter.dev.parent); |
---|
| 381 | + return ret; |
---|
385 | 382 | } |
---|
386 | 383 | |
---|
387 | 384 | static struct riic_irq_desc riic_irqs[] = { |
---|
.. | .. |
---|
440 | 437 | |
---|
441 | 438 | i2c_parse_fw_timings(&pdev->dev, &i2c_t, true); |
---|
442 | 439 | |
---|
| 440 | + pm_runtime_enable(&pdev->dev); |
---|
| 441 | + |
---|
443 | 442 | ret = riic_init_hw(riic, &i2c_t); |
---|
444 | 443 | if (ret) |
---|
445 | | - return ret; |
---|
446 | | - |
---|
| 444 | + goto out; |
---|
447 | 445 | |
---|
448 | 446 | ret = i2c_add_adapter(adap); |
---|
449 | 447 | if (ret) |
---|
450 | | - return ret; |
---|
| 448 | + goto out; |
---|
451 | 449 | |
---|
452 | 450 | platform_set_drvdata(pdev, riic); |
---|
453 | 451 | |
---|
454 | 452 | dev_info(&pdev->dev, "registered with %dHz bus speed\n", |
---|
455 | 453 | i2c_t.bus_freq_hz); |
---|
456 | 454 | return 0; |
---|
| 455 | + |
---|
| 456 | +out: |
---|
| 457 | + pm_runtime_disable(&pdev->dev); |
---|
| 458 | + return ret; |
---|
457 | 459 | } |
---|
458 | 460 | |
---|
459 | 461 | static int riic_i2c_remove(struct platform_device *pdev) |
---|
460 | 462 | { |
---|
461 | 463 | struct riic_dev *riic = platform_get_drvdata(pdev); |
---|
462 | 464 | |
---|
| 465 | + pm_runtime_get_sync(&pdev->dev); |
---|
463 | 466 | writeb(0, riic->base + RIIC_ICIER); |
---|
| 467 | + pm_runtime_put(&pdev->dev); |
---|
464 | 468 | i2c_del_adapter(&riic->adapter); |
---|
| 469 | + pm_runtime_disable(&pdev->dev); |
---|
465 | 470 | |
---|
466 | 471 | return 0; |
---|
467 | 472 | } |
---|