aboutsummaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authorTony Lindgren <tony@atomide.com>2012-11-21 12:46:19 -0500
committerTony Lindgren <tony@atomide.com>2012-11-21 12:46:19 -0500
commit48b0023607c4e524e893a7a378a1dd42234c41a7 (patch)
treedec8ce3b8dab55ecbc65f71f716236fdab95acd3
parent9dc57643738f9fbe45c10cc062903d5dfda5bdd9 (diff)
parent258e84af9799b8c81cf856dcbd8e2d4cc082741d (diff)
Merge branch 'cleanup-timer' of git://github.com/jonhunter/linux into omap-for-v3.8/timer
-rw-r--r--arch/arm/mach-omap1/timer.c1
-rw-r--r--arch/arm/mach-omap1/timer32k.c1
-rw-r--r--arch/arm/mach-omap2/omap_hwmod_2420_data.c1
-rw-r--r--arch/arm/mach-omap2/omap_hwmod_2430_data.c1
-rw-r--r--arch/arm/mach-omap2/pm-debug.c1
-rw-r--r--arch/arm/mach-omap2/timer.c36
-rw-r--r--arch/arm/plat-omap/dmtimer.c54
-rw-r--r--arch/arm/plat-omap/include/plat/dmtimer.h80
-rw-r--r--drivers/staging/tidspbridge/core/ue_deh.c1
-rw-r--r--include/linux/platform_data/dmtimer-omap.h31
10 files changed, 105 insertions, 102 deletions
diff --git a/arch/arm/mach-omap1/timer.c b/arch/arm/mach-omap1/timer.c
index cdeb9d3ef640..bde7a35e5000 100644
--- a/arch/arm/mach-omap1/timer.c
+++ b/arch/arm/mach-omap1/timer.c
@@ -25,6 +25,7 @@
25#include <linux/err.h> 25#include <linux/err.h>
26#include <linux/slab.h> 26#include <linux/slab.h>
27#include <linux/platform_device.h> 27#include <linux/platform_device.h>
28#include <linux/platform_data/dmtimer-omap.h>
28 29
29#include <mach/irqs.h> 30#include <mach/irqs.h>
30 31
diff --git a/arch/arm/mach-omap1/timer32k.c b/arch/arm/mach-omap1/timer32k.c
index 89368195bf08..41152fadd4c0 100644
--- a/arch/arm/mach-omap1/timer32k.c
+++ b/arch/arm/mach-omap1/timer32k.c
@@ -51,7 +51,6 @@
51#include <asm/mach/time.h> 51#include <asm/mach/time.h>
52 52
53#include <plat/counter-32k.h> 53#include <plat/counter-32k.h>
54#include <plat/dmtimer.h>
55 54
56#include <mach/hardware.h> 55#include <mach/hardware.h>
57 56
diff --git a/arch/arm/mach-omap2/omap_hwmod_2420_data.c b/arch/arm/mach-omap2/omap_hwmod_2420_data.c
index a8b3368dca3d..e8efe3d1da6c 100644
--- a/arch/arm/mach-omap2/omap_hwmod_2420_data.c
+++ b/arch/arm/mach-omap2/omap_hwmod_2420_data.c
@@ -17,7 +17,6 @@
17#include <linux/platform_data/spi-omap2-mcspi.h> 17#include <linux/platform_data/spi-omap2-mcspi.h>
18 18
19#include <plat-omap/dma-omap.h> 19#include <plat-omap/dma-omap.h>
20#include <plat/dmtimer.h>
21 20
22#include "omap_hwmod.h" 21#include "omap_hwmod.h"
23#include "l3_2xxx.h" 22#include "l3_2xxx.h"
diff --git a/arch/arm/mach-omap2/omap_hwmod_2430_data.c b/arch/arm/mach-omap2/omap_hwmod_2430_data.c
index dc768c50e523..32d17e3fd727 100644
--- a/arch/arm/mach-omap2/omap_hwmod_2430_data.c
+++ b/arch/arm/mach-omap2/omap_hwmod_2430_data.c
@@ -18,7 +18,6 @@
18#include <linux/platform_data/spi-omap2-mcspi.h> 18#include <linux/platform_data/spi-omap2-mcspi.h>
19 19
20#include <plat-omap/dma-omap.h> 20#include <plat-omap/dma-omap.h>
21#include <plat/dmtimer.h>
22 21
23#include "omap_hwmod.h" 22#include "omap_hwmod.h"
24#include "mmc.h" 23#include "mmc.h"
diff --git a/arch/arm/mach-omap2/pm-debug.c b/arch/arm/mach-omap2/pm-debug.c
index 3cf4fdfd7ab0..e2c291f52f92 100644
--- a/arch/arm/mach-omap2/pm-debug.c
+++ b/arch/arm/mach-omap2/pm-debug.c
@@ -30,7 +30,6 @@
30#include "clock.h" 30#include "clock.h"
31#include "powerdomain.h" 31#include "powerdomain.h"
32#include "clockdomain.h" 32#include "clockdomain.h"
33#include <plat/dmtimer.h>
34#include "omap-pm.h" 33#include "omap-pm.h"
35 34
36#include "soc.h" 35#include "soc.h"
diff --git a/arch/arm/mach-omap2/timer.c b/arch/arm/mach-omap2/timer.c
index 099e4060afe9..b7f43a28e41f 100644
--- a/arch/arm/mach-omap2/timer.c
+++ b/arch/arm/mach-omap2/timer.c
@@ -39,6 +39,8 @@
39#include <linux/of.h> 39#include <linux/of.h>
40#include <linux/of_address.h> 40#include <linux/of_address.h>
41#include <linux/of_irq.h> 41#include <linux/of_irq.h>
42#include <linux/platform_device.h>
43#include <linux/platform_data/dmtimer-omap.h>
42 44
43#include <asm/mach/time.h> 45#include <asm/mach/time.h>
44#include <asm/smp_twd.h> 46#include <asm/smp_twd.h>
@@ -160,11 +162,6 @@ static struct of_device_id omap_timer_match[] __initdata = {
160 { } 162 { }
161}; 163};
162 164
163static struct of_device_id omap_counter_match[] __initdata = {
164 { .compatible = "ti,omap-counter32k", },
165 { }
166};
167
168/** 165/**
169 * omap_get_timer_dt - get a timer using device-tree 166 * omap_get_timer_dt - get a timer using device-tree
170 * @match - device-tree match structure for matching a device type 167 * @match - device-tree match structure for matching a device type
@@ -245,10 +242,8 @@ static int __init omap_dm_timer_init_one(struct omap_dm_timer *timer,
245 const char *oh_name; 242 const char *oh_name;
246 struct device_node *np; 243 struct device_node *np;
247 struct omap_hwmod *oh; 244 struct omap_hwmod *oh;
248 struct resource irq_rsrc, mem_rsrc; 245 struct resource irq, mem;
249 size_t size; 246 int r = 0;
250 int res = 0;
251 int r;
252 247
253 if (of_have_populated_dt()) { 248 if (of_have_populated_dt()) {
254 np = omap_get_timer_dt(omap_timer_match, NULL); 249 np = omap_get_timer_dt(omap_timer_match, NULL);
@@ -280,20 +275,18 @@ static int __init omap_dm_timer_init_one(struct omap_dm_timer *timer,
280 275
281 if (!of_have_populated_dt()) { 276 if (!of_have_populated_dt()) {
282 r = omap_hwmod_get_resource_byname(oh, IORESOURCE_IRQ, NULL, 277 r = omap_hwmod_get_resource_byname(oh, IORESOURCE_IRQ, NULL,
283 &irq_rsrc); 278 &irq);
284 if (r) 279 if (r)
285 return -ENXIO; 280 return -ENXIO;
286 timer->irq = irq_rsrc.start; 281 timer->irq = irq.start;
287 282
288 r = omap_hwmod_get_resource_byname(oh, IORESOURCE_MEM, NULL, 283 r = omap_hwmod_get_resource_byname(oh, IORESOURCE_MEM, NULL,
289 &mem_rsrc); 284 &mem);
290 if (r) 285 if (r)
291 return -ENXIO; 286 return -ENXIO;
292 timer->phys_base = mem_rsrc.start;
293 size = mem_rsrc.end - mem_rsrc.start;
294 287
295 /* Static mapping, never released */ 288 /* Static mapping, never released */
296 timer->io_base = ioremap(timer->phys_base, size); 289 timer->io_base = ioremap(mem.start, mem.end - mem.start);
297 } 290 }
298 291
299 if (!timer->io_base) 292 if (!timer->io_base)
@@ -310,10 +303,10 @@ static int __init omap_dm_timer_init_one(struct omap_dm_timer *timer,
310 303
311 src = clk_get(NULL, fck_source); 304 src = clk_get(NULL, fck_source);
312 if (IS_ERR(src)) { 305 if (IS_ERR(src)) {
313 res = -EINVAL; 306 r = -EINVAL;
314 } else { 307 } else {
315 res = clk_set_parent(timer->fclk, src); 308 r = clk_set_parent(timer->fclk, src);
316 if (IS_ERR_VALUE(res)) 309 if (IS_ERR_VALUE(r))
317 pr_warn("%s: %s cannot set source\n", 310 pr_warn("%s: %s cannot set source\n",
318 __func__, oh->name); 311 __func__, oh->name);
319 clk_put(src); 312 clk_put(src);
@@ -334,7 +327,7 @@ static int __init omap_dm_timer_init_one(struct omap_dm_timer *timer,
334 timer->rate = clk_get_rate(timer->fclk); 327 timer->rate = clk_get_rate(timer->fclk);
335 timer->reserved = 1; 328 timer->reserved = 1;
336 329
337 return res; 330 return r;
338} 331}
339 332
340static void __init omap2_gp_clockevent_init(int gptimer_id, 333static void __init omap2_gp_clockevent_init(int gptimer_id,
@@ -408,6 +401,11 @@ static u32 notrace dmtimer_read_sched_clock(void)
408} 401}
409 402
410#ifdef CONFIG_OMAP_32K_TIMER 403#ifdef CONFIG_OMAP_32K_TIMER
404static struct of_device_id omap_counter_match[] __initdata = {
405 { .compatible = "ti,omap-counter32k", },
406 { }
407};
408
411/* Setup free-running counter for clocksource */ 409/* Setup free-running counter for clocksource */
412static int __init omap2_sync32k_clocksource_init(void) 410static int __init omap2_sync32k_clocksource_init(void)
413{ 411{
diff --git a/arch/arm/plat-omap/dmtimer.c b/arch/arm/plat-omap/dmtimer.c
index 9deeb3064d33..89585c293554 100644
--- a/arch/arm/plat-omap/dmtimer.c
+++ b/arch/arm/plat-omap/dmtimer.c
@@ -43,6 +43,8 @@
43#include <linux/pm_runtime.h> 43#include <linux/pm_runtime.h>
44#include <linux/of.h> 44#include <linux/of.h>
45#include <linux/of_device.h> 45#include <linux/of_device.h>
46#include <linux/platform_device.h>
47#include <linux/platform_data/dmtimer-omap.h>
46 48
47#include <plat/dmtimer.h> 49#include <plat/dmtimer.h>
48 50
@@ -99,32 +101,39 @@ static void omap_timer_restore_context(struct omap_dm_timer *timer)
99 timer->context.tclr); 101 timer->context.tclr);
100} 102}
101 103
102static void omap_dm_timer_wait_for_reset(struct omap_dm_timer *timer) 104static int omap_dm_timer_reset(struct omap_dm_timer *timer)
103{ 105{
104 int c; 106 u32 l, timeout = 100000;
105 107
106 if (!timer->sys_stat) 108 if (timer->revision != 1)
107 return; 109 return -EINVAL;
108 110
109 c = 0; 111 omap_dm_timer_write_reg(timer, OMAP_TIMER_IF_CTRL_REG, 0x06);
110 while (!(__raw_readl(timer->sys_stat) & 1)) { 112
111 c++; 113 do {
112 if (c > 100000) { 114 l = __omap_dm_timer_read(timer,
113 printk(KERN_ERR "Timer failed to reset\n"); 115 OMAP_TIMER_V1_SYS_STAT_OFFSET, 0);
114 return; 116 } while (!l && timeout--);
115 } 117
118 if (!timeout) {
119 dev_err(&timer->pdev->dev, "Timer failed to reset\n");
120 return -ETIMEDOUT;
116 } 121 }
117}
118 122
119static void omap_dm_timer_reset(struct omap_dm_timer *timer) 123 /* Configure timer for smart-idle mode */
120{ 124 l = __omap_dm_timer_read(timer, OMAP_TIMER_OCP_CFG_OFFSET, 0);
121 omap_dm_timer_write_reg(timer, OMAP_TIMER_IF_CTRL_REG, 0x06); 125 l |= 0x2 << 0x3;
122 omap_dm_timer_wait_for_reset(timer); 126 __omap_dm_timer_write(timer, OMAP_TIMER_OCP_CFG_OFFSET, l, 0);
123 __omap_dm_timer_reset(timer, 0, 0); 127
128 timer->posted = 0;
129
130 return 0;
124} 131}
125 132
126int omap_dm_timer_prepare(struct omap_dm_timer *timer) 133static int omap_dm_timer_prepare(struct omap_dm_timer *timer)
127{ 134{
135 int rc;
136
128 /* 137 /*
129 * FIXME: OMAP1 devices do not use the clock framework for dmtimers so 138 * FIXME: OMAP1 devices do not use the clock framework for dmtimers so
130 * do not call clk_get() for these devices. 139 * do not call clk_get() for these devices.
@@ -140,8 +149,13 @@ int omap_dm_timer_prepare(struct omap_dm_timer *timer)
140 149
141 omap_dm_timer_enable(timer); 150 omap_dm_timer_enable(timer);
142 151
143 if (timer->capability & OMAP_TIMER_NEEDS_RESET) 152 if (timer->capability & OMAP_TIMER_NEEDS_RESET) {
144 omap_dm_timer_reset(timer); 153 rc = omap_dm_timer_reset(timer);
154 if (rc) {
155 omap_dm_timer_disable(timer);
156 return rc;
157 }
158 }
145 159
146 __omap_dm_timer_enable_posted(timer); 160 __omap_dm_timer_enable_posted(timer);
147 omap_dm_timer_disable(timer); 161 omap_dm_timer_disable(timer);
diff --git a/arch/arm/plat-omap/include/plat/dmtimer.h b/arch/arm/plat-omap/include/plat/dmtimer.h
index 05a36e16f3f4..a3fbc48c332e 100644
--- a/arch/arm/plat-omap/include/plat/dmtimer.h
+++ b/arch/arm/plat-omap/include/plat/dmtimer.h
@@ -79,8 +79,6 @@ struct omap_timer_capability_dev_attr {
79 u32 timer_capability; 79 u32 timer_capability;
80}; 80};
81 81
82struct omap_dm_timer;
83
84struct timer_regs { 82struct timer_regs {
85 u32 tidr; 83 u32 tidr;
86 u32 tier; 84 u32 tier;
@@ -101,12 +99,29 @@ struct timer_regs {
101 u32 towr; 99 u32 towr;
102}; 100};
103 101
104struct dmtimer_platform_data { 102struct omap_dm_timer {
105 /* set_timer_src - Only used for OMAP1 devices */ 103 int id;
106 int (*set_timer_src)(struct platform_device *pdev, int source); 104 int irq;
107 u32 timer_errata; 105 struct clk *fclk;
108 u32 timer_capability; 106
107 void __iomem *io_base;
108 void __iomem *irq_stat; /* TISR/IRQSTATUS interrupt status */
109 void __iomem *irq_ena; /* irq enable */
110 void __iomem *irq_dis; /* irq disable, only on v2 ip */
111 void __iomem *pend; /* write pending */
112 void __iomem *func_base; /* function register base */
113
114 unsigned long rate;
115 unsigned reserved:1;
116 unsigned posted:1;
117 struct timer_regs context;
109 int (*get_context_loss_count)(struct device *); 118 int (*get_context_loss_count)(struct device *);
119 int ctx_loss_count;
120 int revision;
121 u32 capability;
122 u32 errata;
123 struct platform_device *pdev;
124 struct list_head node;
110}; 125};
111 126
112int omap_dm_timer_reserve_systimer(int id); 127int omap_dm_timer_reserve_systimer(int id);
@@ -260,35 +275,6 @@ int omap_dm_timers_active(void);
260#define OMAP_TIMER_TICK_INT_MASK_COUNT_REG \ 275#define OMAP_TIMER_TICK_INT_MASK_COUNT_REG \
261 (_OMAP_TIMER_TICK_INT_MASK_COUNT_OFFSET | (WP_TOWR << WPSHIFT)) 276 (_OMAP_TIMER_TICK_INT_MASK_COUNT_OFFSET | (WP_TOWR << WPSHIFT))
262 277
263struct omap_dm_timer {
264 unsigned long phys_base;
265 int id;
266 int irq;
267 struct clk *fclk;
268
269 void __iomem *io_base;
270 void __iomem *sys_stat; /* TISTAT timer status */
271 void __iomem *irq_stat; /* TISR/IRQSTATUS interrupt status */
272 void __iomem *irq_ena; /* irq enable */
273 void __iomem *irq_dis; /* irq disable, only on v2 ip */
274 void __iomem *pend; /* write pending */
275 void __iomem *func_base; /* function register base */
276
277 unsigned long rate;
278 unsigned reserved:1;
279 unsigned posted:1;
280 struct timer_regs context;
281 int (*get_context_loss_count)(struct device *);
282 int ctx_loss_count;
283 int revision;
284 u32 capability;
285 u32 errata;
286 struct platform_device *pdev;
287 struct list_head node;
288};
289
290int omap_dm_timer_prepare(struct omap_dm_timer *timer);
291
292static inline u32 __omap_dm_timer_read(struct omap_dm_timer *timer, u32 reg, 278static inline u32 __omap_dm_timer_read(struct omap_dm_timer *timer, u32 reg,
293 int posted) 279 int posted)
294{ 280{
@@ -317,8 +303,6 @@ static inline void __omap_dm_timer_init_regs(struct omap_dm_timer *timer)
317 tidr = __raw_readl(timer->io_base); 303 tidr = __raw_readl(timer->io_base);
318 if (!(tidr >> 16)) { 304 if (!(tidr >> 16)) {
319 timer->revision = 1; 305 timer->revision = 1;
320 timer->sys_stat = timer->io_base +
321 OMAP_TIMER_V1_SYS_STAT_OFFSET;
322 timer->irq_stat = timer->io_base + OMAP_TIMER_V1_STAT_OFFSET; 306 timer->irq_stat = timer->io_base + OMAP_TIMER_V1_STAT_OFFSET;
323 timer->irq_ena = timer->io_base + OMAP_TIMER_V1_INT_EN_OFFSET; 307 timer->irq_ena = timer->io_base + OMAP_TIMER_V1_INT_EN_OFFSET;
324 timer->irq_dis = timer->io_base + OMAP_TIMER_V1_INT_EN_OFFSET; 308 timer->irq_dis = timer->io_base + OMAP_TIMER_V1_INT_EN_OFFSET;
@@ -326,7 +310,6 @@ static inline void __omap_dm_timer_init_regs(struct omap_dm_timer *timer)
326 timer->func_base = timer->io_base; 310 timer->func_base = timer->io_base;
327 } else { 311 } else {
328 timer->revision = 2; 312 timer->revision = 2;
329 timer->sys_stat = NULL;
330 timer->irq_stat = timer->io_base + OMAP_TIMER_V2_IRQSTATUS; 313 timer->irq_stat = timer->io_base + OMAP_TIMER_V2_IRQSTATUS;
331 timer->irq_ena = timer->io_base + OMAP_TIMER_V2_IRQENABLE_SET; 314 timer->irq_ena = timer->io_base + OMAP_TIMER_V2_IRQENABLE_SET;
332 timer->irq_dis = timer->io_base + OMAP_TIMER_V2_IRQENABLE_CLR; 315 timer->irq_dis = timer->io_base + OMAP_TIMER_V2_IRQENABLE_CLR;
@@ -337,25 +320,6 @@ static inline void __omap_dm_timer_init_regs(struct omap_dm_timer *timer)
337 } 320 }
338} 321}
339 322
340/* Assumes the source clock has been set by caller */
341static inline void __omap_dm_timer_reset(struct omap_dm_timer *timer,
342 int autoidle, int wakeup)
343{
344 u32 l;
345
346 l = __raw_readl(timer->io_base + OMAP_TIMER_OCP_CFG_OFFSET);
347 l |= 0x02 << 3; /* Set to smart-idle mode */
348 l |= 0x2 << 8; /* Set clock activity to perserve f-clock on idle */
349
350 if (autoidle)
351 l |= 0x1 << 0;
352
353 if (wakeup)
354 l |= 1 << 2;
355
356 __raw_writel(l, timer->io_base + OMAP_TIMER_OCP_CFG_OFFSET);
357}
358
359/* 323/*
360 * __omap_dm_timer_enable_posted - enables write posted mode 324 * __omap_dm_timer_enable_posted - enables write posted mode
361 * @timer: pointer to timer instance handle 325 * @timer: pointer to timer instance handle
diff --git a/drivers/staging/tidspbridge/core/ue_deh.c b/drivers/staging/tidspbridge/core/ue_deh.c
index 3d28b2345fbd..6aea6f1b4982 100644
--- a/drivers/staging/tidspbridge/core/ue_deh.c
+++ b/drivers/staging/tidspbridge/core/ue_deh.c
@@ -19,7 +19,6 @@
19 19
20#include <linux/kernel.h> 20#include <linux/kernel.h>
21#include <linux/interrupt.h> 21#include <linux/interrupt.h>
22#include <plat/dmtimer.h>
23 22
24#include <dspbridge/dbdefs.h> 23#include <dspbridge/dbdefs.h>
25#include <dspbridge/dspdeh.h> 24#include <dspbridge/dspdeh.h>
diff --git a/include/linux/platform_data/dmtimer-omap.h b/include/linux/platform_data/dmtimer-omap.h
new file mode 100644
index 000000000000..a19b78d826e9
--- /dev/null
+++ b/include/linux/platform_data/dmtimer-omap.h
@@ -0,0 +1,31 @@
1/*
2 * DMTIMER platform data for TI OMAP platforms
3 *
4 * Copyright (C) 2012 Texas Instruments
5 * Author: Jon Hunter <jon-hunter@ti.com>
6 *
7 * This program is free software; you can redistribute it and/or modify it
8 * under the terms of the GNU General Public License version 2 as published by
9 * the Free Software Foundation.
10 *
11 * This program is distributed in the hope that it will be useful, but WITHOUT
12 * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
13 * FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for
14 * more details.
15 *
16 * You should have received a copy of the GNU General Public License along with
17 * this program. If not, see <http://www.gnu.org/licenses/>.
18 */
19
20#ifndef __PLATFORM_DATA_DMTIMER_OMAP_H__
21#define __PLATFORM_DATA_DMTIMER_OMAP_H__
22
23struct dmtimer_platform_data {
24 /* set_timer_src - Only used for OMAP1 devices */
25 int (*set_timer_src)(struct platform_device *pdev, int source);
26 u32 timer_capability;
27 u32 timer_errata;
28 int (*get_context_loss_count)(struct device *);
29};
30
31#endif /* __PLATFORM_DATA_DMTIMER_OMAP_H__ */