Skip to content

Commit

Permalink
ARM: OMAP: convert I2C driver to PM QoS for MPU latency constraints
Browse files Browse the repository at this point in the history
Convert the driver from the outdated omap_pm_set_max_mpu_wakeup_lat
API to the new PM QoS API.
Since the constraint is on the MPU subsystem, use the PM_QOS_CPU_DMA_LATENCY
class of PM QoS. The resulting MPU constraints are used by cpuidle to
decide the next power state of the MPU subsystem.

The I2C device latency timing is derived from the FIFO size and the
clock speed and so is applicable to all OMAP SoCs.

Signed-off-by: Jean Pihet <j-pihet@ti.com>
Acked-by: Shubhrajyoti D <shubhrajyoti@ti.com>
Acked-by: Tony Lindgren <tony@atomide.com>
Acked-by: Kevin Hilman <khilman@ti.com>
Signed-off-by: Wolfram Sang <w.sang@pengutronix.de>
  • Loading branch information
Jean Pihet authored and Wolfram Sang committed Oct 6, 2012
1 parent 43fea58 commit 3db11fe
Show file tree
Hide file tree
Showing 3 changed files with 18 additions and 36 deletions.
21 changes: 0 additions & 21 deletions arch/arm/plat-omap/i2c.c
Original file line number Diff line number Diff line change
Expand Up @@ -26,15 +26,13 @@
#include <linux/kernel.h>
#include <linux/platform_device.h>
#include <linux/i2c.h>
#include <linux/i2c-omap.h>
#include <linux/slab.h>
#include <linux/err.h>
#include <linux/clk.h>

#include <mach/irqs.h>
#include <plat/mux.h>
#include <plat/i2c.h>
#include <plat/omap-pm.h>
#include <plat/omap_device.h>

#define OMAP_I2C_SIZE 0x3f
Expand Down Expand Up @@ -129,16 +127,6 @@ static inline int omap1_i2c_add_bus(int bus_id)


#ifdef CONFIG_ARCH_OMAP2PLUS
/*
* XXX This function is a temporary compatibility wrapper - only
* needed until the I2C driver can be converted to call
* omap_pm_set_max_dev_wakeup_lat() and handle a return code.
*/
static void omap_pm_set_max_mpu_wakeup_lat_compat(struct device *dev, long t)
{
omap_pm_set_max_mpu_wakeup_lat(dev, t);
}

static inline int omap2_i2c_add_bus(int bus_id)
{
int l;
Expand Down Expand Up @@ -170,15 +158,6 @@ static inline int omap2_i2c_add_bus(int bus_id)
dev_attr = (struct omap_i2c_dev_attr *)oh->dev_attr;
pdata->flags = dev_attr->flags;

/*
* When waiting for completion of a i2c transfer, we need to
* set a wake up latency constraint for the MPU. This is to
* ensure quick enough wakeup from idle, when transfer
* completes.
* Only omap3 has support for constraints
*/
if (cpu_is_omap34xx())
pdata->set_mpu_wkup_lat = omap_pm_set_max_mpu_wakeup_lat_compat;
pdev = omap_device_build(name, bus_id, oh, pdata,
sizeof(struct omap_i2c_bus_platform_data),
NULL, 0, 0);
Expand Down
32 changes: 18 additions & 14 deletions drivers/i2c/busses/i2c-omap.c
Original file line number Diff line number Diff line change
Expand Up @@ -43,6 +43,7 @@
#include <linux/slab.h>
#include <linux/i2c-omap.h>
#include <linux/pm_runtime.h>
#include <linux/pm_qos.h>

/* I2C controller revisions */
#define OMAP_I2C_OMAP1_REV_2 0x20
Expand Down Expand Up @@ -186,9 +187,8 @@ struct omap_i2c_dev {
int reg_shift; /* bit shift for I2C register addresses */
struct completion cmd_complete;
struct resource *ioarea;
u32 latency; /* maximum mpu wkup latency */
void (*set_mpu_wkup_lat)(struct device *dev,
long latency);
u32 latency; /* maximum MPU wkup latency */
struct pm_qos_request pm_qos_request;
u32 speed; /* Speed of bus in kHz */
u32 dtrev; /* extra revision from DT */
u32 flags;
Expand Down Expand Up @@ -494,9 +494,7 @@ static void omap_i2c_resize_fifo(struct omap_i2c_dev *dev, u8 size, bool is_rx)
dev->b_hw = 1; /* Enable hardware fixes */

/* calculate wakeup latency constraint for MPU */
if (dev->set_mpu_wkup_lat != NULL)
dev->latency = (1000000 * dev->threshold) /
(1000 * dev->speed / 8);
dev->latency = (1000000 * dev->threshold) / (1000 * dev->speed / 8);
}

/*
Expand Down Expand Up @@ -631,17 +629,25 @@ omap_i2c_xfer(struct i2c_adapter *adap, struct i2c_msg msgs[], int num)
if (r < 0)
goto out;

if (dev->set_mpu_wkup_lat != NULL)
dev->set_mpu_wkup_lat(dev->dev, dev->latency);
/*
* When waiting for completion of a i2c transfer, we need to
* set a wake up latency constraint for the MPU. This is to
* ensure quick enough wakeup from idle, when transfer
* completes.
*/
if (dev->latency)
pm_qos_add_request(&dev->pm_qos_request,
PM_QOS_CPU_DMA_LATENCY,
dev->latency);

for (i = 0; i < num; i++) {
r = omap_i2c_xfer_msg(adap, &msgs[i], (i == (num - 1)));
if (r != 0)
break;
}

if (dev->set_mpu_wkup_lat != NULL)
dev->set_mpu_wkup_lat(dev->dev, -1);
if (dev->latency)
pm_qos_remove_request(&dev->pm_qos_request);

if (r == 0)
r = num;
Expand Down Expand Up @@ -1097,7 +1103,6 @@ omap_i2c_probe(struct platform_device *pdev)
} else if (pdata != NULL) {
dev->speed = pdata->clkrate;
dev->flags = pdata->flags;
dev->set_mpu_wkup_lat = pdata->set_mpu_wkup_lat;
dev->dtrev = pdata->rev;
}

Expand Down Expand Up @@ -1153,9 +1158,8 @@ omap_i2c_probe(struct platform_device *pdev)
dev->b_hw = 1; /* Enable hardware fixes */

/* calculate wakeup latency constraint for MPU */
if (dev->set_mpu_wkup_lat != NULL)
dev->latency = (1000000 * dev->fifo_size) /
(1000 * dev->speed / 8);
dev->latency = (1000000 * dev->fifo_size) /
(1000 * dev->speed / 8);
}

/* reset ASAP, clearing any IRQs */
Expand Down
1 change: 0 additions & 1 deletion include/linux/i2c-omap.h
Original file line number Diff line number Diff line change
Expand Up @@ -34,7 +34,6 @@ struct omap_i2c_bus_platform_data {
u32 clkrate;
u32 rev;
u32 flags;
void (*set_mpu_wkup_lat)(struct device *dev, long set);
};

#endif

0 comments on commit 3db11fe

Please sign in to comment.