0001
0002
0003
0004
0005
0006
0007
0008
0009
0010
0011
0012
0013
0014
0015
0016
0017
0018
0019
0020
0021 #include <linux/clk.h>
0022 #include <linux/clk-provider.h>
0023 #include <linux/cpu_pm.h>
0024 #include <linux/module.h>
0025 #include <linux/io.h>
0026 #include <linux/device.h>
0027 #include <linux/err.h>
0028 #include <linux/pm_runtime.h>
0029 #include <linux/of.h>
0030 #include <linux/of_device.h>
0031 #include <linux/platform_device.h>
0032 #include <linux/platform_data/dmtimer-omap.h>
0033
0034 #include <clocksource/timer-ti-dm.h>
0035
0036 static u32 omap_reserved_systimers;
0037 static LIST_HEAD(omap_timer_list);
0038 static DEFINE_SPINLOCK(dm_timer_lock);
0039
0040 enum {
0041 REQUEST_ANY = 0,
0042 REQUEST_BY_ID,
0043 REQUEST_BY_CAP,
0044 REQUEST_BY_NODE,
0045 };
0046
0047 static inline u32 __omap_dm_timer_read(struct omap_dm_timer *timer, u32 reg,
0048 int posted)
0049 {
0050 if (posted)
0051 while (readl_relaxed(timer->pend) & (reg >> WPSHIFT))
0052 cpu_relax();
0053
0054 return readl_relaxed(timer->func_base + (reg & 0xff));
0055 }
0056
0057 static inline void __omap_dm_timer_write(struct omap_dm_timer *timer,
0058 u32 reg, u32 val, int posted)
0059 {
0060 if (posted)
0061 while (readl_relaxed(timer->pend) & (reg >> WPSHIFT))
0062 cpu_relax();
0063
0064 writel_relaxed(val, timer->func_base + (reg & 0xff));
0065 }
0066
0067 static inline void __omap_dm_timer_init_regs(struct omap_dm_timer *timer)
0068 {
0069 u32 tidr;
0070
0071
0072 tidr = readl_relaxed(timer->io_base);
0073 if (!(tidr >> 16)) {
0074 timer->revision = 1;
0075 timer->irq_stat = timer->io_base + OMAP_TIMER_V1_STAT_OFFSET;
0076 timer->irq_ena = timer->io_base + OMAP_TIMER_V1_INT_EN_OFFSET;
0077 timer->irq_dis = timer->io_base + OMAP_TIMER_V1_INT_EN_OFFSET;
0078 timer->pend = timer->io_base + _OMAP_TIMER_WRITE_PEND_OFFSET;
0079 timer->func_base = timer->io_base;
0080 } else {
0081 timer->revision = 2;
0082 timer->irq_stat = timer->io_base + OMAP_TIMER_V2_IRQSTATUS;
0083 timer->irq_ena = timer->io_base + OMAP_TIMER_V2_IRQENABLE_SET;
0084 timer->irq_dis = timer->io_base + OMAP_TIMER_V2_IRQENABLE_CLR;
0085 timer->pend = timer->io_base +
0086 _OMAP_TIMER_WRITE_PEND_OFFSET +
0087 OMAP_TIMER_V2_FUNC_OFFSET;
0088 timer->func_base = timer->io_base + OMAP_TIMER_V2_FUNC_OFFSET;
0089 }
0090 }
0091
0092
0093
0094
0095
0096
0097
0098
0099
0100
0101
0102 static inline void __omap_dm_timer_enable_posted(struct omap_dm_timer *timer)
0103 {
0104 if (timer->posted)
0105 return;
0106
0107 if (timer->errata & OMAP_TIMER_ERRATA_I103_I767) {
0108 timer->posted = OMAP_TIMER_NONPOSTED;
0109 __omap_dm_timer_write(timer, OMAP_TIMER_IF_CTRL_REG, 0, 0);
0110 return;
0111 }
0112
0113 __omap_dm_timer_write(timer, OMAP_TIMER_IF_CTRL_REG,
0114 OMAP_TIMER_CTRL_POSTED, 0);
0115 timer->context.tsicr = OMAP_TIMER_CTRL_POSTED;
0116 timer->posted = OMAP_TIMER_POSTED;
0117 }
0118
0119 static inline void __omap_dm_timer_stop(struct omap_dm_timer *timer,
0120 int posted, unsigned long rate)
0121 {
0122 u32 l;
0123
0124 l = __omap_dm_timer_read(timer, OMAP_TIMER_CTRL_REG, posted);
0125 if (l & OMAP_TIMER_CTRL_ST) {
0126 l &= ~0x1;
0127 __omap_dm_timer_write(timer, OMAP_TIMER_CTRL_REG, l, posted);
0128 #ifdef CONFIG_ARCH_OMAP2PLUS
0129
0130 __omap_dm_timer_read(timer, OMAP_TIMER_CTRL_REG, posted);
0131
0132
0133
0134
0135 udelay(3500000 / rate + 1);
0136 #endif
0137 }
0138
0139
0140 writel_relaxed(OMAP_TIMER_INT_OVERFLOW, timer->irq_stat);
0141 }
0142
0143 static inline void __omap_dm_timer_int_enable(struct omap_dm_timer *timer,
0144 unsigned int value)
0145 {
0146 writel_relaxed(value, timer->irq_ena);
0147 __omap_dm_timer_write(timer, OMAP_TIMER_WAKEUP_EN_REG, value, 0);
0148 }
0149
0150 static inline unsigned int
0151 __omap_dm_timer_read_counter(struct omap_dm_timer *timer, int posted)
0152 {
0153 return __omap_dm_timer_read(timer, OMAP_TIMER_COUNTER_REG, posted);
0154 }
0155
0156 static inline void __omap_dm_timer_write_status(struct omap_dm_timer *timer,
0157 unsigned int value)
0158 {
0159 writel_relaxed(value, timer->irq_stat);
0160 }
0161
0162
0163
0164
0165
0166
0167
0168
0169
0170
0171 static inline u32 omap_dm_timer_read_reg(struct omap_dm_timer *timer, u32 reg)
0172 {
0173 WARN_ON((reg & 0xff) < _OMAP_TIMER_WAKEUP_EN_OFFSET);
0174 return __omap_dm_timer_read(timer, reg, timer->posted);
0175 }
0176
0177
0178
0179
0180
0181
0182
0183
0184
0185
0186
0187 static void omap_dm_timer_write_reg(struct omap_dm_timer *timer, u32 reg,
0188 u32 value)
0189 {
0190 WARN_ON((reg & 0xff) < _OMAP_TIMER_WAKEUP_EN_OFFSET);
0191 __omap_dm_timer_write(timer, reg, value, timer->posted);
0192 }
0193
0194 static void omap_timer_restore_context(struct omap_dm_timer *timer)
0195 {
0196 __omap_dm_timer_write(timer, OMAP_TIMER_OCP_CFG_OFFSET,
0197 timer->context.ocp_cfg, 0);
0198
0199 omap_dm_timer_write_reg(timer, OMAP_TIMER_WAKEUP_EN_REG,
0200 timer->context.twer);
0201 omap_dm_timer_write_reg(timer, OMAP_TIMER_COUNTER_REG,
0202 timer->context.tcrr);
0203 omap_dm_timer_write_reg(timer, OMAP_TIMER_LOAD_REG,
0204 timer->context.tldr);
0205 omap_dm_timer_write_reg(timer, OMAP_TIMER_MATCH_REG,
0206 timer->context.tmar);
0207 omap_dm_timer_write_reg(timer, OMAP_TIMER_IF_CTRL_REG,
0208 timer->context.tsicr);
0209 writel_relaxed(timer->context.tier, timer->irq_ena);
0210 omap_dm_timer_write_reg(timer, OMAP_TIMER_CTRL_REG,
0211 timer->context.tclr);
0212 }
0213
0214 static void omap_timer_save_context(struct omap_dm_timer *timer)
0215 {
0216 timer->context.ocp_cfg =
0217 __omap_dm_timer_read(timer, OMAP_TIMER_OCP_CFG_OFFSET, 0);
0218
0219 timer->context.tclr =
0220 omap_dm_timer_read_reg(timer, OMAP_TIMER_CTRL_REG);
0221 timer->context.twer =
0222 omap_dm_timer_read_reg(timer, OMAP_TIMER_WAKEUP_EN_REG);
0223 timer->context.tldr =
0224 omap_dm_timer_read_reg(timer, OMAP_TIMER_LOAD_REG);
0225 timer->context.tmar =
0226 omap_dm_timer_read_reg(timer, OMAP_TIMER_MATCH_REG);
0227 timer->context.tier = readl_relaxed(timer->irq_ena);
0228 timer->context.tsicr =
0229 omap_dm_timer_read_reg(timer, OMAP_TIMER_IF_CTRL_REG);
0230 }
0231
0232 static int omap_timer_context_notifier(struct notifier_block *nb,
0233 unsigned long cmd, void *v)
0234 {
0235 struct omap_dm_timer *timer;
0236
0237 timer = container_of(nb, struct omap_dm_timer, nb);
0238
0239 switch (cmd) {
0240 case CPU_CLUSTER_PM_ENTER:
0241 if ((timer->capability & OMAP_TIMER_ALWON) ||
0242 !atomic_read(&timer->enabled))
0243 break;
0244 omap_timer_save_context(timer);
0245 break;
0246 case CPU_CLUSTER_PM_ENTER_FAILED:
0247 break;
0248 case CPU_CLUSTER_PM_EXIT:
0249 if ((timer->capability & OMAP_TIMER_ALWON) ||
0250 !atomic_read(&timer->enabled))
0251 break;
0252 omap_timer_restore_context(timer);
0253 break;
0254 }
0255
0256 return NOTIFY_OK;
0257 }
0258
0259 static int omap_dm_timer_reset(struct omap_dm_timer *timer)
0260 {
0261 u32 l, timeout = 100000;
0262
0263 if (timer->revision != 1)
0264 return -EINVAL;
0265
0266 omap_dm_timer_write_reg(timer, OMAP_TIMER_IF_CTRL_REG, 0x06);
0267
0268 do {
0269 l = __omap_dm_timer_read(timer,
0270 OMAP_TIMER_V1_SYS_STAT_OFFSET, 0);
0271 } while (!l && timeout--);
0272
0273 if (!timeout) {
0274 dev_err(&timer->pdev->dev, "Timer failed to reset\n");
0275 return -ETIMEDOUT;
0276 }
0277
0278
0279 l = __omap_dm_timer_read(timer, OMAP_TIMER_OCP_CFG_OFFSET, 0);
0280 l |= 0x2 << 0x3;
0281 __omap_dm_timer_write(timer, OMAP_TIMER_OCP_CFG_OFFSET, l, 0);
0282
0283 timer->posted = 0;
0284
0285 return 0;
0286 }
0287
0288 static int omap_dm_timer_set_source(struct omap_dm_timer *timer, int source)
0289 {
0290 int ret;
0291 const char *parent_name;
0292 struct clk *parent;
0293 struct dmtimer_platform_data *pdata;
0294
0295 if (unlikely(!timer) || IS_ERR(timer->fclk))
0296 return -EINVAL;
0297
0298 switch (source) {
0299 case OMAP_TIMER_SRC_SYS_CLK:
0300 parent_name = "timer_sys_ck";
0301 break;
0302 case OMAP_TIMER_SRC_32_KHZ:
0303 parent_name = "timer_32k_ck";
0304 break;
0305 case OMAP_TIMER_SRC_EXT_CLK:
0306 parent_name = "timer_ext_ck";
0307 break;
0308 default:
0309 return -EINVAL;
0310 }
0311
0312 pdata = timer->pdev->dev.platform_data;
0313
0314
0315
0316
0317
0318
0319 if (pdata && pdata->set_timer_src)
0320 return pdata->set_timer_src(timer->pdev, source);
0321
0322 #if defined(CONFIG_COMMON_CLK)
0323
0324 if (clk_hw_get_num_parents(__clk_get_hw(timer->fclk)) < 2)
0325 return 0;
0326 #endif
0327
0328 parent = clk_get(&timer->pdev->dev, parent_name);
0329 if (IS_ERR(parent)) {
0330 pr_err("%s: %s not found\n", __func__, parent_name);
0331 return -EINVAL;
0332 }
0333
0334 ret = clk_set_parent(timer->fclk, parent);
0335 if (ret < 0)
0336 pr_err("%s: failed to set %s as parent\n", __func__,
0337 parent_name);
0338
0339 clk_put(parent);
0340
0341 return ret;
0342 }
0343
0344 static void omap_dm_timer_enable(struct omap_dm_timer *timer)
0345 {
0346 pm_runtime_get_sync(&timer->pdev->dev);
0347 }
0348
0349 static void omap_dm_timer_disable(struct omap_dm_timer *timer)
0350 {
0351 pm_runtime_put_sync(&timer->pdev->dev);
0352 }
0353
0354 static int omap_dm_timer_prepare(struct omap_dm_timer *timer)
0355 {
0356 int rc;
0357
0358
0359
0360
0361
0362 if (!(timer->capability & OMAP_TIMER_NEEDS_RESET)) {
0363 timer->fclk = clk_get(&timer->pdev->dev, "fck");
0364 if (WARN_ON_ONCE(IS_ERR(timer->fclk))) {
0365 dev_err(&timer->pdev->dev, ": No fclk handle.\n");
0366 return -EINVAL;
0367 }
0368 }
0369
0370 omap_dm_timer_enable(timer);
0371
0372 if (timer->capability & OMAP_TIMER_NEEDS_RESET) {
0373 rc = omap_dm_timer_reset(timer);
0374 if (rc) {
0375 omap_dm_timer_disable(timer);
0376 return rc;
0377 }
0378 }
0379
0380 __omap_dm_timer_enable_posted(timer);
0381 omap_dm_timer_disable(timer);
0382
0383 return 0;
0384 }
0385
0386 static inline u32 omap_dm_timer_reserved_systimer(int id)
0387 {
0388 return (omap_reserved_systimers & (1 << (id - 1))) ? 1 : 0;
0389 }
0390
0391 int omap_dm_timer_reserve_systimer(int id)
0392 {
0393 if (omap_dm_timer_reserved_systimer(id))
0394 return -ENODEV;
0395
0396 omap_reserved_systimers |= (1 << (id - 1));
0397
0398 return 0;
0399 }
0400
0401 static struct omap_dm_timer *_omap_dm_timer_request(int req_type, void *data)
0402 {
0403 struct omap_dm_timer *timer = NULL, *t;
0404 struct device_node *np = NULL;
0405 unsigned long flags;
0406 u32 cap = 0;
0407 int id = 0;
0408
0409 switch (req_type) {
0410 case REQUEST_BY_ID:
0411 id = *(int *)data;
0412 break;
0413 case REQUEST_BY_CAP:
0414 cap = *(u32 *)data;
0415 break;
0416 case REQUEST_BY_NODE:
0417 np = (struct device_node *)data;
0418 break;
0419 default:
0420
0421 break;
0422 }
0423
0424 spin_lock_irqsave(&dm_timer_lock, flags);
0425 list_for_each_entry(t, &omap_timer_list, node) {
0426 if (t->reserved)
0427 continue;
0428
0429 switch (req_type) {
0430 case REQUEST_BY_ID:
0431 if (id == t->pdev->id) {
0432 timer = t;
0433 timer->reserved = 1;
0434 goto found;
0435 }
0436 break;
0437 case REQUEST_BY_CAP:
0438 if (cap == (t->capability & cap)) {
0439
0440
0441
0442
0443
0444
0445
0446
0447 if (timer)
0448 timer->reserved = 0;
0449 timer = t;
0450 timer->reserved = 1;
0451
0452
0453 if (t->capability == cap)
0454 goto found;
0455 }
0456 break;
0457 case REQUEST_BY_NODE:
0458 if (np == t->pdev->dev.of_node) {
0459 timer = t;
0460 timer->reserved = 1;
0461 goto found;
0462 }
0463 break;
0464 default:
0465
0466 timer = t;
0467 timer->reserved = 1;
0468 goto found;
0469 }
0470 }
0471 found:
0472 spin_unlock_irqrestore(&dm_timer_lock, flags);
0473
0474 if (timer && omap_dm_timer_prepare(timer)) {
0475 timer->reserved = 0;
0476 timer = NULL;
0477 }
0478
0479 if (!timer)
0480 pr_debug("%s: timer request failed!\n", __func__);
0481
0482 return timer;
0483 }
0484
0485 static struct omap_dm_timer *omap_dm_timer_request(void)
0486 {
0487 return _omap_dm_timer_request(REQUEST_ANY, NULL);
0488 }
0489
0490 static struct omap_dm_timer *omap_dm_timer_request_specific(int id)
0491 {
0492
0493 if (of_have_populated_dt()) {
0494 pr_warn("%s: Please use omap_dm_timer_request_by_node()\n",
0495 __func__);
0496 return NULL;
0497 }
0498
0499 return _omap_dm_timer_request(REQUEST_BY_ID, &id);
0500 }
0501
0502
0503
0504
0505
0506
0507
0508
0509
0510
0511 struct omap_dm_timer *omap_dm_timer_request_by_cap(u32 cap)
0512 {
0513 return _omap_dm_timer_request(REQUEST_BY_CAP, &cap);
0514 }
0515
0516
0517
0518
0519
0520
0521
0522
0523 static struct omap_dm_timer *omap_dm_timer_request_by_node(struct device_node *np)
0524 {
0525 if (!np)
0526 return NULL;
0527
0528 return _omap_dm_timer_request(REQUEST_BY_NODE, np);
0529 }
0530
0531 static int omap_dm_timer_free(struct omap_dm_timer *timer)
0532 {
0533 if (unlikely(!timer))
0534 return -EINVAL;
0535
0536 clk_put(timer->fclk);
0537
0538 WARN_ON(!timer->reserved);
0539 timer->reserved = 0;
0540 return 0;
0541 }
0542
0543 int omap_dm_timer_get_irq(struct omap_dm_timer *timer)
0544 {
0545 if (timer)
0546 return timer->irq;
0547 return -EINVAL;
0548 }
0549
0550 #if defined(CONFIG_ARCH_OMAP1)
0551 #include <linux/soc/ti/omap1-io.h>
0552
0553 static struct clk *omap_dm_timer_get_fclk(struct omap_dm_timer *timer)
0554 {
0555 return NULL;
0556 }
0557
0558
0559
0560
0561
0562 __u32 omap_dm_timer_modify_idlect_mask(__u32 inputmask)
0563 {
0564 int i = 0;
0565 struct omap_dm_timer *timer = NULL;
0566 unsigned long flags;
0567
0568
0569 if (!(inputmask & (1 << 1)))
0570 return inputmask;
0571
0572
0573 spin_lock_irqsave(&dm_timer_lock, flags);
0574 list_for_each_entry(timer, &omap_timer_list, node) {
0575 u32 l;
0576
0577 l = omap_dm_timer_read_reg(timer, OMAP_TIMER_CTRL_REG);
0578 if (l & OMAP_TIMER_CTRL_ST) {
0579 if (((omap_readl(MOD_CONF_CTRL_1) >> (i * 2)) & 0x03) == 0)
0580 inputmask &= ~(1 << 1);
0581 else
0582 inputmask &= ~(1 << 2);
0583 }
0584 i++;
0585 }
0586 spin_unlock_irqrestore(&dm_timer_lock, flags);
0587
0588 return inputmask;
0589 }
0590
0591 #else
0592
0593 static struct clk *omap_dm_timer_get_fclk(struct omap_dm_timer *timer)
0594 {
0595 if (timer && !IS_ERR(timer->fclk))
0596 return timer->fclk;
0597 return NULL;
0598 }
0599
0600 __u32 omap_dm_timer_modify_idlect_mask(__u32 inputmask)
0601 {
0602 BUG();
0603
0604 return 0;
0605 }
0606
0607 #endif
0608
0609 int omap_dm_timer_trigger(struct omap_dm_timer *timer)
0610 {
0611 if (unlikely(!timer || !atomic_read(&timer->enabled))) {
0612 pr_err("%s: timer not available or enabled.\n", __func__);
0613 return -EINVAL;
0614 }
0615
0616 omap_dm_timer_write_reg(timer, OMAP_TIMER_TRIGGER_REG, 0);
0617 return 0;
0618 }
0619
0620 static int omap_dm_timer_start(struct omap_dm_timer *timer)
0621 {
0622 u32 l;
0623
0624 if (unlikely(!timer))
0625 return -EINVAL;
0626
0627 omap_dm_timer_enable(timer);
0628
0629 l = omap_dm_timer_read_reg(timer, OMAP_TIMER_CTRL_REG);
0630 if (!(l & OMAP_TIMER_CTRL_ST)) {
0631 l |= OMAP_TIMER_CTRL_ST;
0632 omap_dm_timer_write_reg(timer, OMAP_TIMER_CTRL_REG, l);
0633 }
0634
0635 return 0;
0636 }
0637
0638 static int omap_dm_timer_stop(struct omap_dm_timer *timer)
0639 {
0640 unsigned long rate = 0;
0641
0642 if (unlikely(!timer))
0643 return -EINVAL;
0644
0645 if (!(timer->capability & OMAP_TIMER_NEEDS_RESET))
0646 rate = clk_get_rate(timer->fclk);
0647
0648 __omap_dm_timer_stop(timer, timer->posted, rate);
0649
0650 omap_dm_timer_disable(timer);
0651 return 0;
0652 }
0653
0654 static int omap_dm_timer_set_load(struct omap_dm_timer *timer,
0655 unsigned int load)
0656 {
0657 if (unlikely(!timer))
0658 return -EINVAL;
0659
0660 omap_dm_timer_enable(timer);
0661 omap_dm_timer_write_reg(timer, OMAP_TIMER_LOAD_REG, load);
0662
0663 omap_dm_timer_disable(timer);
0664 return 0;
0665 }
0666
0667 static int omap_dm_timer_set_match(struct omap_dm_timer *timer, int enable,
0668 unsigned int match)
0669 {
0670 u32 l;
0671
0672 if (unlikely(!timer))
0673 return -EINVAL;
0674
0675 omap_dm_timer_enable(timer);
0676 l = omap_dm_timer_read_reg(timer, OMAP_TIMER_CTRL_REG);
0677 if (enable)
0678 l |= OMAP_TIMER_CTRL_CE;
0679 else
0680 l &= ~OMAP_TIMER_CTRL_CE;
0681 omap_dm_timer_write_reg(timer, OMAP_TIMER_MATCH_REG, match);
0682 omap_dm_timer_write_reg(timer, OMAP_TIMER_CTRL_REG, l);
0683
0684 omap_dm_timer_disable(timer);
0685 return 0;
0686 }
0687
0688 static int omap_dm_timer_set_pwm(struct omap_dm_timer *timer, int def_on,
0689 int toggle, int trigger, int autoreload)
0690 {
0691 u32 l;
0692
0693 if (unlikely(!timer))
0694 return -EINVAL;
0695
0696 omap_dm_timer_enable(timer);
0697 l = omap_dm_timer_read_reg(timer, OMAP_TIMER_CTRL_REG);
0698 l &= ~(OMAP_TIMER_CTRL_GPOCFG | OMAP_TIMER_CTRL_SCPWM |
0699 OMAP_TIMER_CTRL_PT | (0x03 << 10) | OMAP_TIMER_CTRL_AR);
0700 if (def_on)
0701 l |= OMAP_TIMER_CTRL_SCPWM;
0702 if (toggle)
0703 l |= OMAP_TIMER_CTRL_PT;
0704 l |= trigger << 10;
0705 if (autoreload)
0706 l |= OMAP_TIMER_CTRL_AR;
0707 omap_dm_timer_write_reg(timer, OMAP_TIMER_CTRL_REG, l);
0708
0709 omap_dm_timer_disable(timer);
0710 return 0;
0711 }
0712
0713 static int omap_dm_timer_get_pwm_status(struct omap_dm_timer *timer)
0714 {
0715 u32 l;
0716
0717 if (unlikely(!timer))
0718 return -EINVAL;
0719
0720 omap_dm_timer_enable(timer);
0721 l = omap_dm_timer_read_reg(timer, OMAP_TIMER_CTRL_REG);
0722 omap_dm_timer_disable(timer);
0723
0724 return l;
0725 }
0726
0727 static int omap_dm_timer_set_prescaler(struct omap_dm_timer *timer,
0728 int prescaler)
0729 {
0730 u32 l;
0731
0732 if (unlikely(!timer) || prescaler < -1 || prescaler > 7)
0733 return -EINVAL;
0734
0735 omap_dm_timer_enable(timer);
0736 l = omap_dm_timer_read_reg(timer, OMAP_TIMER_CTRL_REG);
0737 l &= ~(OMAP_TIMER_CTRL_PRE | (0x07 << 2));
0738 if (prescaler >= 0) {
0739 l |= OMAP_TIMER_CTRL_PRE;
0740 l |= prescaler << 2;
0741 }
0742 omap_dm_timer_write_reg(timer, OMAP_TIMER_CTRL_REG, l);
0743
0744 omap_dm_timer_disable(timer);
0745 return 0;
0746 }
0747
0748 static int omap_dm_timer_set_int_enable(struct omap_dm_timer *timer,
0749 unsigned int value)
0750 {
0751 if (unlikely(!timer))
0752 return -EINVAL;
0753
0754 omap_dm_timer_enable(timer);
0755 __omap_dm_timer_int_enable(timer, value);
0756
0757 omap_dm_timer_disable(timer);
0758 return 0;
0759 }
0760
0761
0762
0763
0764
0765
0766
0767
0768 static int omap_dm_timer_set_int_disable(struct omap_dm_timer *timer, u32 mask)
0769 {
0770 u32 l = mask;
0771
0772 if (unlikely(!timer))
0773 return -EINVAL;
0774
0775 omap_dm_timer_enable(timer);
0776
0777 if (timer->revision == 1)
0778 l = readl_relaxed(timer->irq_ena) & ~mask;
0779
0780 writel_relaxed(l, timer->irq_dis);
0781 l = omap_dm_timer_read_reg(timer, OMAP_TIMER_WAKEUP_EN_REG) & ~mask;
0782 omap_dm_timer_write_reg(timer, OMAP_TIMER_WAKEUP_EN_REG, l);
0783
0784 omap_dm_timer_disable(timer);
0785 return 0;
0786 }
0787
0788 static unsigned int omap_dm_timer_read_status(struct omap_dm_timer *timer)
0789 {
0790 unsigned int l;
0791
0792 if (unlikely(!timer || !atomic_read(&timer->enabled))) {
0793 pr_err("%s: timer not available or enabled.\n", __func__);
0794 return 0;
0795 }
0796
0797 l = readl_relaxed(timer->irq_stat);
0798
0799 return l;
0800 }
0801
0802 static int omap_dm_timer_write_status(struct omap_dm_timer *timer, unsigned int value)
0803 {
0804 if (unlikely(!timer || !atomic_read(&timer->enabled)))
0805 return -EINVAL;
0806
0807 __omap_dm_timer_write_status(timer, value);
0808
0809 return 0;
0810 }
0811
0812 static unsigned int omap_dm_timer_read_counter(struct omap_dm_timer *timer)
0813 {
0814 if (unlikely(!timer || !atomic_read(&timer->enabled))) {
0815 pr_err("%s: timer not iavailable or enabled.\n", __func__);
0816 return 0;
0817 }
0818
0819 return __omap_dm_timer_read_counter(timer, timer->posted);
0820 }
0821
0822 static int omap_dm_timer_write_counter(struct omap_dm_timer *timer, unsigned int value)
0823 {
0824 if (unlikely(!timer || !atomic_read(&timer->enabled))) {
0825 pr_err("%s: timer not available or enabled.\n", __func__);
0826 return -EINVAL;
0827 }
0828
0829 omap_dm_timer_write_reg(timer, OMAP_TIMER_COUNTER_REG, value);
0830
0831
0832 timer->context.tcrr = value;
0833 return 0;
0834 }
0835
0836 int omap_dm_timers_active(void)
0837 {
0838 struct omap_dm_timer *timer;
0839
0840 list_for_each_entry(timer, &omap_timer_list, node) {
0841 if (!timer->reserved)
0842 continue;
0843
0844 if (omap_dm_timer_read_reg(timer, OMAP_TIMER_CTRL_REG) &
0845 OMAP_TIMER_CTRL_ST) {
0846 return 1;
0847 }
0848 }
0849 return 0;
0850 }
0851
0852 static int __maybe_unused omap_dm_timer_runtime_suspend(struct device *dev)
0853 {
0854 struct omap_dm_timer *timer = dev_get_drvdata(dev);
0855
0856 atomic_set(&timer->enabled, 0);
0857
0858 if (timer->capability & OMAP_TIMER_ALWON || !timer->func_base)
0859 return 0;
0860
0861 omap_timer_save_context(timer);
0862
0863 return 0;
0864 }
0865
0866 static int __maybe_unused omap_dm_timer_runtime_resume(struct device *dev)
0867 {
0868 struct omap_dm_timer *timer = dev_get_drvdata(dev);
0869
0870 if (!(timer->capability & OMAP_TIMER_ALWON) && timer->func_base)
0871 omap_timer_restore_context(timer);
0872
0873 atomic_set(&timer->enabled, 1);
0874
0875 return 0;
0876 }
0877
0878 static const struct dev_pm_ops omap_dm_timer_pm_ops = {
0879 SET_RUNTIME_PM_OPS(omap_dm_timer_runtime_suspend,
0880 omap_dm_timer_runtime_resume, NULL)
0881 };
0882
0883 static const struct of_device_id omap_timer_match[];
0884
0885
0886
0887
0888
0889
0890
0891
0892 static int omap_dm_timer_probe(struct platform_device *pdev)
0893 {
0894 unsigned long flags;
0895 struct omap_dm_timer *timer;
0896 struct device *dev = &pdev->dev;
0897 const struct dmtimer_platform_data *pdata;
0898 int ret;
0899
0900 pdata = of_device_get_match_data(dev);
0901 if (!pdata)
0902 pdata = dev_get_platdata(dev);
0903 else
0904 dev->platform_data = (void *)pdata;
0905
0906 if (!pdata) {
0907 dev_err(dev, "%s: no platform data.\n", __func__);
0908 return -ENODEV;
0909 }
0910
0911 timer = devm_kzalloc(dev, sizeof(*timer), GFP_KERNEL);
0912 if (!timer)
0913 return -ENOMEM;
0914
0915 timer->irq = platform_get_irq(pdev, 0);
0916 if (timer->irq < 0)
0917 return timer->irq;
0918
0919 timer->fclk = ERR_PTR(-ENODEV);
0920 timer->io_base = devm_platform_ioremap_resource(pdev, 0);
0921 if (IS_ERR(timer->io_base))
0922 return PTR_ERR(timer->io_base);
0923
0924 platform_set_drvdata(pdev, timer);
0925
0926 if (dev->of_node) {
0927 if (of_find_property(dev->of_node, "ti,timer-alwon", NULL))
0928 timer->capability |= OMAP_TIMER_ALWON;
0929 if (of_find_property(dev->of_node, "ti,timer-dsp", NULL))
0930 timer->capability |= OMAP_TIMER_HAS_DSP_IRQ;
0931 if (of_find_property(dev->of_node, "ti,timer-pwm", NULL))
0932 timer->capability |= OMAP_TIMER_HAS_PWM;
0933 if (of_find_property(dev->of_node, "ti,timer-secure", NULL))
0934 timer->capability |= OMAP_TIMER_SECURE;
0935 } else {
0936 timer->id = pdev->id;
0937 timer->capability = pdata->timer_capability;
0938 timer->reserved = omap_dm_timer_reserved_systimer(timer->id);
0939 }
0940
0941 if (!(timer->capability & OMAP_TIMER_ALWON)) {
0942 timer->nb.notifier_call = omap_timer_context_notifier;
0943 cpu_pm_register_notifier(&timer->nb);
0944 }
0945
0946 timer->errata = pdata->timer_errata;
0947
0948 timer->pdev = pdev;
0949
0950 pm_runtime_enable(dev);
0951
0952 if (!timer->reserved) {
0953 ret = pm_runtime_get_sync(dev);
0954 if (ret < 0) {
0955 dev_err(dev, "%s: pm_runtime_get_sync failed!\n",
0956 __func__);
0957 goto err_get_sync;
0958 }
0959 __omap_dm_timer_init_regs(timer);
0960 pm_runtime_put(dev);
0961 }
0962
0963
0964 spin_lock_irqsave(&dm_timer_lock, flags);
0965 list_add_tail(&timer->node, &omap_timer_list);
0966 spin_unlock_irqrestore(&dm_timer_lock, flags);
0967
0968 dev_dbg(dev, "Device Probed.\n");
0969
0970 return 0;
0971
0972 err_get_sync:
0973 pm_runtime_put_noidle(dev);
0974 pm_runtime_disable(dev);
0975 return ret;
0976 }
0977
0978
0979
0980
0981
0982
0983
0984
0985
0986 static int omap_dm_timer_remove(struct platform_device *pdev)
0987 {
0988 struct omap_dm_timer *timer;
0989 unsigned long flags;
0990 int ret = -EINVAL;
0991
0992 spin_lock_irqsave(&dm_timer_lock, flags);
0993 list_for_each_entry(timer, &omap_timer_list, node)
0994 if (!strcmp(dev_name(&timer->pdev->dev),
0995 dev_name(&pdev->dev))) {
0996 if (!(timer->capability & OMAP_TIMER_ALWON))
0997 cpu_pm_unregister_notifier(&timer->nb);
0998 list_del(&timer->node);
0999 ret = 0;
1000 break;
1001 }
1002 spin_unlock_irqrestore(&dm_timer_lock, flags);
1003
1004 pm_runtime_disable(&pdev->dev);
1005
1006 return ret;
1007 }
1008
1009 static const struct omap_dm_timer_ops dmtimer_ops = {
1010 .request_by_node = omap_dm_timer_request_by_node,
1011 .request_specific = omap_dm_timer_request_specific,
1012 .request = omap_dm_timer_request,
1013 .set_source = omap_dm_timer_set_source,
1014 .get_irq = omap_dm_timer_get_irq,
1015 .set_int_enable = omap_dm_timer_set_int_enable,
1016 .set_int_disable = omap_dm_timer_set_int_disable,
1017 .free = omap_dm_timer_free,
1018 .enable = omap_dm_timer_enable,
1019 .disable = omap_dm_timer_disable,
1020 .get_fclk = omap_dm_timer_get_fclk,
1021 .start = omap_dm_timer_start,
1022 .stop = omap_dm_timer_stop,
1023 .set_load = omap_dm_timer_set_load,
1024 .set_match = omap_dm_timer_set_match,
1025 .set_pwm = omap_dm_timer_set_pwm,
1026 .get_pwm_status = omap_dm_timer_get_pwm_status,
1027 .set_prescaler = omap_dm_timer_set_prescaler,
1028 .read_counter = omap_dm_timer_read_counter,
1029 .write_counter = omap_dm_timer_write_counter,
1030 .read_status = omap_dm_timer_read_status,
1031 .write_status = omap_dm_timer_write_status,
1032 };
1033
1034 static const struct dmtimer_platform_data omap3plus_pdata = {
1035 .timer_errata = OMAP_TIMER_ERRATA_I103_I767,
1036 .timer_ops = &dmtimer_ops,
1037 };
1038
1039 static const struct dmtimer_platform_data am6_pdata = {
1040 .timer_ops = &dmtimer_ops,
1041 };
1042
1043 static const struct of_device_id omap_timer_match[] = {
1044 {
1045 .compatible = "ti,omap2420-timer",
1046 },
1047 {
1048 .compatible = "ti,omap3430-timer",
1049 .data = &omap3plus_pdata,
1050 },
1051 {
1052 .compatible = "ti,omap4430-timer",
1053 .data = &omap3plus_pdata,
1054 },
1055 {
1056 .compatible = "ti,omap5430-timer",
1057 .data = &omap3plus_pdata,
1058 },
1059 {
1060 .compatible = "ti,am335x-timer",
1061 .data = &omap3plus_pdata,
1062 },
1063 {
1064 .compatible = "ti,am335x-timer-1ms",
1065 .data = &omap3plus_pdata,
1066 },
1067 {
1068 .compatible = "ti,dm816-timer",
1069 .data = &omap3plus_pdata,
1070 },
1071 {
1072 .compatible = "ti,am654-timer",
1073 .data = &am6_pdata,
1074 },
1075 {},
1076 };
1077 MODULE_DEVICE_TABLE(of, omap_timer_match);
1078
1079 static struct platform_driver omap_dm_timer_driver = {
1080 .probe = omap_dm_timer_probe,
1081 .remove = omap_dm_timer_remove,
1082 .driver = {
1083 .name = "omap_timer",
1084 .of_match_table = of_match_ptr(omap_timer_match),
1085 .pm = &omap_dm_timer_pm_ops,
1086 },
1087 };
1088
1089 module_platform_driver(omap_dm_timer_driver);
1090
1091 MODULE_DESCRIPTION("OMAP Dual-Mode Timer Driver");
1092 MODULE_LICENSE("GPL");
1093 MODULE_AUTHOR("Texas Instruments Inc");