Back to home page

OSCL-LXR

 
 

    


0001 // SPDX-License-Identifier: GPL-2.0-only
0002 /*
0003  * A RTC driver for the Simtek STK17TA8
0004  *
0005  * By Thomas Hommel <thomas.hommel@ge.com>
0006  *
0007  * Based on the DS1553 driver from
0008  * Atsushi Nemoto <anemo@mba.ocn.ne.jp>
0009  */
0010 
0011 #include <linux/bcd.h>
0012 #include <linux/init.h>
0013 #include <linux/kernel.h>
0014 #include <linux/gfp.h>
0015 #include <linux/delay.h>
0016 #include <linux/jiffies.h>
0017 #include <linux/interrupt.h>
0018 #include <linux/rtc.h>
0019 #include <linux/platform_device.h>
0020 #include <linux/io.h>
0021 #include <linux/module.h>
0022 
0023 #define RTC_REG_SIZE        0x20000
0024 #define RTC_OFFSET      0x1fff0
0025 
0026 #define RTC_FLAGS       (RTC_OFFSET + 0)
0027 #define RTC_CENTURY     (RTC_OFFSET + 1)
0028 #define RTC_SECONDS_ALARM   (RTC_OFFSET + 2)
0029 #define RTC_MINUTES_ALARM   (RTC_OFFSET + 3)
0030 #define RTC_HOURS_ALARM     (RTC_OFFSET + 4)
0031 #define RTC_DATE_ALARM      (RTC_OFFSET + 5)
0032 #define RTC_INTERRUPTS      (RTC_OFFSET + 6)
0033 #define RTC_WATCHDOG        (RTC_OFFSET + 7)
0034 #define RTC_CALIBRATION     (RTC_OFFSET + 8)
0035 #define RTC_SECONDS     (RTC_OFFSET + 9)
0036 #define RTC_MINUTES     (RTC_OFFSET + 10)
0037 #define RTC_HOURS       (RTC_OFFSET + 11)
0038 #define RTC_DAY         (RTC_OFFSET + 12)
0039 #define RTC_DATE        (RTC_OFFSET + 13)
0040 #define RTC_MONTH       (RTC_OFFSET + 14)
0041 #define RTC_YEAR        (RTC_OFFSET + 15)
0042 
0043 #define RTC_SECONDS_MASK    0x7f
0044 #define RTC_DAY_MASK        0x07
0045 #define RTC_CAL_MASK        0x3f
0046 
0047 /* Bits in the Calibration register */
0048 #define RTC_STOP        0x80
0049 
0050 /* Bits in the Flags register */
0051 #define RTC_FLAGS_AF        0x40
0052 #define RTC_FLAGS_PF        0x20
0053 #define RTC_WRITE       0x02
0054 #define RTC_READ        0x01
0055 
0056 /* Bits in the Interrupts register */
0057 #define RTC_INTS_AIE        0x40
0058 
0059 struct rtc_plat_data {
0060     struct rtc_device *rtc;
0061     void __iomem *ioaddr;
0062     unsigned long last_jiffies;
0063     int irq;
0064     unsigned int irqen;
0065     int alrm_sec;
0066     int alrm_min;
0067     int alrm_hour;
0068     int alrm_mday;
0069     spinlock_t lock;
0070 };
0071 
0072 static int stk17ta8_rtc_set_time(struct device *dev, struct rtc_time *tm)
0073 {
0074     struct rtc_plat_data *pdata = dev_get_drvdata(dev);
0075     void __iomem *ioaddr = pdata->ioaddr;
0076     u8 flags;
0077 
0078     flags = readb(pdata->ioaddr + RTC_FLAGS);
0079     writeb(flags | RTC_WRITE, pdata->ioaddr + RTC_FLAGS);
0080 
0081     writeb(bin2bcd(tm->tm_year % 100), ioaddr + RTC_YEAR);
0082     writeb(bin2bcd(tm->tm_mon + 1), ioaddr + RTC_MONTH);
0083     writeb(bin2bcd(tm->tm_wday) & RTC_DAY_MASK, ioaddr + RTC_DAY);
0084     writeb(bin2bcd(tm->tm_mday), ioaddr + RTC_DATE);
0085     writeb(bin2bcd(tm->tm_hour), ioaddr + RTC_HOURS);
0086     writeb(bin2bcd(tm->tm_min), ioaddr + RTC_MINUTES);
0087     writeb(bin2bcd(tm->tm_sec) & RTC_SECONDS_MASK, ioaddr + RTC_SECONDS);
0088     writeb(bin2bcd((tm->tm_year + 1900) / 100), ioaddr + RTC_CENTURY);
0089 
0090     writeb(flags & ~RTC_WRITE, pdata->ioaddr + RTC_FLAGS);
0091     return 0;
0092 }
0093 
0094 static int stk17ta8_rtc_read_time(struct device *dev, struct rtc_time *tm)
0095 {
0096     struct rtc_plat_data *pdata = dev_get_drvdata(dev);
0097     void __iomem *ioaddr = pdata->ioaddr;
0098     unsigned int year, month, day, hour, minute, second, week;
0099     unsigned int century;
0100     u8 flags;
0101 
0102     /* give enough time to update RTC in case of continuous read */
0103     if (pdata->last_jiffies == jiffies)
0104         msleep(1);
0105     pdata->last_jiffies = jiffies;
0106 
0107     flags = readb(pdata->ioaddr + RTC_FLAGS);
0108     writeb(flags | RTC_READ, ioaddr + RTC_FLAGS);
0109     second = readb(ioaddr + RTC_SECONDS) & RTC_SECONDS_MASK;
0110     minute = readb(ioaddr + RTC_MINUTES);
0111     hour = readb(ioaddr + RTC_HOURS);
0112     day = readb(ioaddr + RTC_DATE);
0113     week = readb(ioaddr + RTC_DAY) & RTC_DAY_MASK;
0114     month = readb(ioaddr + RTC_MONTH);
0115     year = readb(ioaddr + RTC_YEAR);
0116     century = readb(ioaddr + RTC_CENTURY);
0117     writeb(flags & ~RTC_READ, ioaddr + RTC_FLAGS);
0118     tm->tm_sec = bcd2bin(second);
0119     tm->tm_min = bcd2bin(minute);
0120     tm->tm_hour = bcd2bin(hour);
0121     tm->tm_mday = bcd2bin(day);
0122     tm->tm_wday = bcd2bin(week);
0123     tm->tm_mon = bcd2bin(month) - 1;
0124     /* year is 1900 + tm->tm_year */
0125     tm->tm_year = bcd2bin(year) + bcd2bin(century) * 100 - 1900;
0126 
0127     return 0;
0128 }
0129 
0130 static void stk17ta8_rtc_update_alarm(struct rtc_plat_data *pdata)
0131 {
0132     void __iomem *ioaddr = pdata->ioaddr;
0133     unsigned long irqflags;
0134     u8 flags;
0135 
0136     spin_lock_irqsave(&pdata->lock, irqflags);
0137 
0138     flags = readb(ioaddr + RTC_FLAGS);
0139     writeb(flags | RTC_WRITE, ioaddr + RTC_FLAGS);
0140 
0141     writeb(pdata->alrm_mday < 0 || (pdata->irqen & RTC_UF) ?
0142            0x80 : bin2bcd(pdata->alrm_mday),
0143            ioaddr + RTC_DATE_ALARM);
0144     writeb(pdata->alrm_hour < 0 || (pdata->irqen & RTC_UF) ?
0145            0x80 : bin2bcd(pdata->alrm_hour),
0146            ioaddr + RTC_HOURS_ALARM);
0147     writeb(pdata->alrm_min < 0 || (pdata->irqen & RTC_UF) ?
0148            0x80 : bin2bcd(pdata->alrm_min),
0149            ioaddr + RTC_MINUTES_ALARM);
0150     writeb(pdata->alrm_sec < 0 || (pdata->irqen & RTC_UF) ?
0151            0x80 : bin2bcd(pdata->alrm_sec),
0152            ioaddr + RTC_SECONDS_ALARM);
0153     writeb(pdata->irqen ? RTC_INTS_AIE : 0, ioaddr + RTC_INTERRUPTS);
0154     readb(ioaddr + RTC_FLAGS);  /* clear interrupts */
0155     writeb(flags & ~RTC_WRITE, ioaddr + RTC_FLAGS);
0156     spin_unlock_irqrestore(&pdata->lock, irqflags);
0157 }
0158 
0159 static int stk17ta8_rtc_set_alarm(struct device *dev, struct rtc_wkalrm *alrm)
0160 {
0161     struct rtc_plat_data *pdata = dev_get_drvdata(dev);
0162 
0163     if (pdata->irq <= 0)
0164         return -EINVAL;
0165     pdata->alrm_mday = alrm->time.tm_mday;
0166     pdata->alrm_hour = alrm->time.tm_hour;
0167     pdata->alrm_min = alrm->time.tm_min;
0168     pdata->alrm_sec = alrm->time.tm_sec;
0169     if (alrm->enabled)
0170         pdata->irqen |= RTC_AF;
0171     stk17ta8_rtc_update_alarm(pdata);
0172     return 0;
0173 }
0174 
0175 static int stk17ta8_rtc_read_alarm(struct device *dev, struct rtc_wkalrm *alrm)
0176 {
0177     struct rtc_plat_data *pdata = dev_get_drvdata(dev);
0178 
0179     if (pdata->irq <= 0)
0180         return -EINVAL;
0181     alrm->time.tm_mday = pdata->alrm_mday < 0 ? 0 : pdata->alrm_mday;
0182     alrm->time.tm_hour = pdata->alrm_hour < 0 ? 0 : pdata->alrm_hour;
0183     alrm->time.tm_min = pdata->alrm_min < 0 ? 0 : pdata->alrm_min;
0184     alrm->time.tm_sec = pdata->alrm_sec < 0 ? 0 : pdata->alrm_sec;
0185     alrm->enabled = (pdata->irqen & RTC_AF) ? 1 : 0;
0186     return 0;
0187 }
0188 
0189 static irqreturn_t stk17ta8_rtc_interrupt(int irq, void *dev_id)
0190 {
0191     struct platform_device *pdev = dev_id;
0192     struct rtc_plat_data *pdata = platform_get_drvdata(pdev);
0193     void __iomem *ioaddr = pdata->ioaddr;
0194     unsigned long events = 0;
0195 
0196     spin_lock(&pdata->lock);
0197     /* read and clear interrupt */
0198     if (readb(ioaddr + RTC_FLAGS) & RTC_FLAGS_AF) {
0199         events = RTC_IRQF;
0200         if (readb(ioaddr + RTC_SECONDS_ALARM) & 0x80)
0201             events |= RTC_UF;
0202         else
0203             events |= RTC_AF;
0204         rtc_update_irq(pdata->rtc, 1, events);
0205     }
0206     spin_unlock(&pdata->lock);
0207     return events ? IRQ_HANDLED : IRQ_NONE;
0208 }
0209 
0210 static int stk17ta8_rtc_alarm_irq_enable(struct device *dev,
0211     unsigned int enabled)
0212 {
0213     struct rtc_plat_data *pdata = dev_get_drvdata(dev);
0214 
0215     if (pdata->irq <= 0)
0216         return -EINVAL;
0217     if (enabled)
0218         pdata->irqen |= RTC_AF;
0219     else
0220         pdata->irqen &= ~RTC_AF;
0221     stk17ta8_rtc_update_alarm(pdata);
0222     return 0;
0223 }
0224 
0225 static const struct rtc_class_ops stk17ta8_rtc_ops = {
0226     .read_time      = stk17ta8_rtc_read_time,
0227     .set_time       = stk17ta8_rtc_set_time,
0228     .read_alarm     = stk17ta8_rtc_read_alarm,
0229     .set_alarm      = stk17ta8_rtc_set_alarm,
0230     .alarm_irq_enable   = stk17ta8_rtc_alarm_irq_enable,
0231 };
0232 
0233 static int stk17ta8_nvram_read(void *priv, unsigned int pos, void *val,
0234                    size_t bytes)
0235 {
0236     struct rtc_plat_data *pdata = priv;
0237     void __iomem *ioaddr = pdata->ioaddr;
0238     u8 *buf = val;
0239 
0240     for (; bytes; bytes--)
0241         *buf++ = readb(ioaddr + pos++);
0242     return 0;
0243 }
0244 
0245 static int stk17ta8_nvram_write(void *priv, unsigned int pos, void *val,
0246                 size_t bytes)
0247 {
0248     struct rtc_plat_data *pdata = priv;
0249     void __iomem *ioaddr = pdata->ioaddr;
0250     u8 *buf = val;
0251 
0252     for (; bytes; bytes--)
0253         writeb(*buf++, ioaddr + pos++);
0254     return 0;
0255 }
0256 
0257 static int stk17ta8_rtc_probe(struct platform_device *pdev)
0258 {
0259     unsigned int cal;
0260     unsigned int flags;
0261     struct rtc_plat_data *pdata;
0262     void __iomem *ioaddr;
0263     int ret = 0;
0264     struct nvmem_config nvmem_cfg = {
0265         .name = "stk17ta8_nvram",
0266         .word_size = 1,
0267         .stride = 1,
0268         .size = RTC_OFFSET,
0269         .reg_read = stk17ta8_nvram_read,
0270         .reg_write = stk17ta8_nvram_write,
0271     };
0272 
0273     pdata = devm_kzalloc(&pdev->dev, sizeof(*pdata), GFP_KERNEL);
0274     if (!pdata)
0275         return -ENOMEM;
0276 
0277     ioaddr = devm_platform_ioremap_resource(pdev, 0);
0278     if (IS_ERR(ioaddr))
0279         return PTR_ERR(ioaddr);
0280     pdata->ioaddr = ioaddr;
0281     pdata->irq = platform_get_irq(pdev, 0);
0282 
0283     /* turn RTC on if it was not on */
0284     cal = readb(ioaddr + RTC_CALIBRATION);
0285     if (cal & RTC_STOP) {
0286         cal &= RTC_CAL_MASK;
0287         flags = readb(ioaddr + RTC_FLAGS);
0288         writeb(flags | RTC_WRITE, ioaddr + RTC_FLAGS);
0289         writeb(cal, ioaddr + RTC_CALIBRATION);
0290         writeb(flags & ~RTC_WRITE, ioaddr + RTC_FLAGS);
0291     }
0292     if (readb(ioaddr + RTC_FLAGS) & RTC_FLAGS_PF)
0293         dev_warn(&pdev->dev, "voltage-low detected.\n");
0294 
0295     spin_lock_init(&pdata->lock);
0296     pdata->last_jiffies = jiffies;
0297     platform_set_drvdata(pdev, pdata);
0298     if (pdata->irq > 0) {
0299         writeb(0, ioaddr + RTC_INTERRUPTS);
0300         if (devm_request_irq(&pdev->dev, pdata->irq,
0301                 stk17ta8_rtc_interrupt,
0302                 IRQF_SHARED,
0303                 pdev->name, pdev) < 0) {
0304             dev_warn(&pdev->dev, "interrupt not available.\n");
0305             pdata->irq = 0;
0306         }
0307     }
0308 
0309     pdata->rtc = devm_rtc_allocate_device(&pdev->dev);
0310     if (IS_ERR(pdata->rtc))
0311         return PTR_ERR(pdata->rtc);
0312 
0313     pdata->rtc->ops = &stk17ta8_rtc_ops;
0314 
0315     nvmem_cfg.priv = pdata;
0316     ret = devm_rtc_nvmem_register(pdata->rtc, &nvmem_cfg);
0317     if (ret)
0318         return ret;
0319 
0320     return devm_rtc_register_device(pdata->rtc);
0321 }
0322 
0323 /* work with hotplug and coldplug */
0324 MODULE_ALIAS("platform:stk17ta8");
0325 
0326 static struct platform_driver stk17ta8_rtc_driver = {
0327     .probe      = stk17ta8_rtc_probe,
0328     .driver     = {
0329         .name   = "stk17ta8",
0330     },
0331 };
0332 
0333 module_platform_driver(stk17ta8_rtc_driver);
0334 
0335 MODULE_AUTHOR("Thomas Hommel <thomas.hommel@ge.com>");
0336 MODULE_DESCRIPTION("Simtek STK17TA8 RTC driver");
0337 MODULE_LICENSE("GPL");