Author: andrew
Date: Thu Jul 22 23:23:39 2010
New Revision: 210397
URL: http://svn.freebsd.org/changeset/base/210397

Log:
  Add the s3c24x0 real time clock driver
  
  Approved by:  imp (mentor)

Added:
  head/sys/arm/s3c2xx0/s3c24x0_rtc.c   (contents, props changed)
Modified:
  head/sys/arm/s3c2xx0/files.s3c2xx0
  head/sys/arm/s3c2xx0/s3c24x0.c
  head/sys/arm/s3c2xx0/s3c24x0reg.h

Modified: head/sys/arm/s3c2xx0/files.s3c2xx0
==============================================================================
--- head/sys/arm/s3c2xx0/files.s3c2xx0  Thu Jul 22 23:12:19 2010        
(r210396)
+++ head/sys/arm/s3c2xx0/files.s3c2xx0  Thu Jul 22 23:23:39 2010        
(r210397)
@@ -2,6 +2,7 @@
 arm/arm/cpufunc_asm_arm9.S     standard
 arm/arm/irq_dispatch.S         standard
 arm/s3c2xx0/board_ln2410sbc.c  optional        board_ln2410sbc
+arm/s3c2xx0/s3c24x0_rtc.c      standard
 arm/s3c2xx0/s3c24x0_machdep.c  standard
 arm/s3c2xx0/s3c24x0.c          standard
 arm/s3c2xx0/s3c2xx0_space.c    standard

Modified: head/sys/arm/s3c2xx0/s3c24x0.c
==============================================================================
--- head/sys/arm/s3c2xx0/s3c24x0.c      Thu Jul 22 23:12:19 2010        
(r210396)
+++ head/sys/arm/s3c2xx0/s3c24x0.c      Thu Jul 22 23:23:39 2010        
(r210397)
@@ -80,6 +80,10 @@ static struct {
                u_long count;
        } res[2];
 } s3c24x0_children[] = {
+       { "rtc", 0, -1, {
+               { SYS_RES_IOPORT, S3C24X0_RTC_PA_BASE, S3C24X0_RTC_SIZE },
+               { 0 },
+       } },
        { "timer", 0, -1, { { 0 }, } },
        { "uart", 1, 0, {
                { SYS_RES_IRQ, S3C24X0_INT_UART0, 1 },

Added: head/sys/arm/s3c2xx0/s3c24x0_rtc.c
==============================================================================
--- /dev/null   00:00:00 1970   (empty, because file is newly added)
+++ head/sys/arm/s3c2xx0/s3c24x0_rtc.c  Thu Jul 22 23:23:39 2010        
(r210397)
@@ -0,0 +1,162 @@
+/*
+ * Copyright (C) 2010 Andrew Turner
+ * All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ * 1. Redistributions of source code must retain the above copyright
+ *    notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ *    notice, this list of conditions and the following disclaimer in the
+ *    documentation and/or other materials provided with the distribution.
+ *
+ * THIS SOFTWARE IS PROVIDED BY THE AUTHOR AND CONTRIBUTORS ``AS IS'' AND
+ * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
+ * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
+ * ARE DISCLAIMED.  IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE LIABLE
+ * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
+ * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
+ * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
+ * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
+ * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
+ * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
+ * SUCH DAMAGE.
+ *
+ */
+
+#include <sys/cdefs.h>
+__FBSDID("$FreeBSD$");
+#include <sys/param.h>
+#include <sys/bus.h>
+#include <sys/time.h>
+#include <sys/clock.h>
+#include <sys/resource.h>
+#include <sys/systm.h>
+#include <sys/rman.h>
+#include <sys/kernel.h>
+#include <sys/module.h>
+
+#include <machine/bus.h>
+
+#include <arm/s3c2xx0/s3c24x0reg.h>
+
+#include "clock_if.h"
+
+#define YEAR_BASE              2000
+
+struct s3c2xx0_rtc_softc {
+       struct resource *mem_res;
+};
+
+static int
+s3c2xx0_rtc_probe(device_t dev)
+{
+
+       device_set_desc(dev, "Samsung Integrated RTC");
+       return (0);
+}
+
+static int
+s3c2xx0_rtc_attach(device_t dev)
+{
+       struct s3c2xx0_rtc_softc *sc;
+       int error, rid;
+
+       sc = device_get_softc(dev);
+       error = 0;
+
+       rid = 0;
+       sc->mem_res = bus_alloc_resource_any(dev, SYS_RES_IOPORT, &rid,
+           RF_ACTIVE);
+       if (sc->mem_res == NULL) {
+               error = ENOMEM;
+               goto out;
+       }
+
+       bus_write_1(sc->mem_res, RTC_RTCCON, RTCCON_RTCEN);
+       clock_register(dev, 1000000);
+
+out:
+       return (error);
+}
+
+static int
+s3c2xx0_rtc_gettime(device_t dev, struct timespec *ts)
+{
+       struct s3c2xx0_rtc_softc *sc;
+       struct clocktime ct;
+
+#define READ_TIME() do {                                               \
+       ct.year = YEAR_BASE + FROMBCD(bus_read_1(sc->mem_res, RTC_BCDYEAR)); \
+       ct.mon = FROMBCD(bus_read_1(sc->mem_res, RTC_BCDMON));          \
+       ct.dow = FROMBCD(bus_read_1(sc->mem_res, RTC_BCDDAY));          \
+       ct.day = FROMBCD(bus_read_1(sc->mem_res, RTC_BCDDATE));         \
+       ct.hour = FROMBCD(bus_read_1(sc->mem_res, RTC_BCDHOUR));        \
+       ct.min = FROMBCD(bus_read_1(sc->mem_res, RTC_BCDMIN));          \
+       ct.sec = FROMBCD(bus_read_1(sc->mem_res, RTC_BCDSEC));          \
+} while (0)
+
+       sc = device_get_softc(dev);
+
+       ct.nsec = 0;
+       READ_TIME();
+       /*
+        * Check if we could have read incorrect values
+        * as the values could have changed.
+        */
+       if (ct.sec == 0) {
+               READ_TIME();
+       }
+
+       ct.dow = -1;
+
+#undef READ_TIME
+       return (clock_ct_to_ts(&ct, ts));
+}
+
+static int
+s3c2xx0_rtc_settime(device_t dev, struct timespec *ts)
+{
+       struct s3c2xx0_rtc_softc *sc;
+       struct clocktime ct;
+
+       sc = device_get_softc(dev);
+
+       /* Resolution: 1 sec */
+       if (ts->tv_nsec >= 500000000)
+               ts->tv_sec++;
+       ts->tv_nsec = 0;
+       clock_ts_to_ct(ts, &ct);
+
+       bus_write_1(sc->mem_res, RTC_BCDSEC, TOBCD(ct.sec));
+       bus_write_1(sc->mem_res, RTC_BCDMIN, TOBCD(ct.min));
+       bus_write_1(sc->mem_res, RTC_BCDHOUR, TOBCD(ct.hour));
+       bus_write_1(sc->mem_res, RTC_BCDDATE, TOBCD(ct.day));
+       bus_write_1(sc->mem_res, RTC_BCDDAY, TOBCD(ct.dow));
+       bus_write_1(sc->mem_res, RTC_BCDMON, TOBCD(ct.mon));
+       bus_write_1(sc->mem_res, RTC_BCDYEAR, TOBCD(ct.year - YEAR_BASE));
+
+       return (0);
+}
+
+static device_method_t s3c2xx0_rtc_methods[] = {
+       DEVMETHOD(device_probe,         s3c2xx0_rtc_probe),
+       DEVMETHOD(device_attach,        s3c2xx0_rtc_attach),
+
+       DEVMETHOD(clock_gettime,        s3c2xx0_rtc_gettime),
+       DEVMETHOD(clock_settime,        s3c2xx0_rtc_settime),
+
+       { 0, 0 },
+};
+
+static driver_t s3c2xx0_rtc_driver = {
+       "rtc",
+       s3c2xx0_rtc_methods,
+       sizeof(struct s3c2xx0_rtc_softc),
+};
+static devclass_t s3c2xx0_rtc_devclass;
+
+DRIVER_MODULE(s3c2xx0_rtc, s3c24x0, s3c2xx0_rtc_driver, s3c2xx0_rtc_devclass,
+    0, 0);
+

Modified: head/sys/arm/s3c2xx0/s3c24x0reg.h
==============================================================================
--- head/sys/arm/s3c2xx0/s3c24x0reg.h   Thu Jul 22 23:12:19 2010        
(r210396)
+++ head/sys/arm/s3c2xx0/s3c24x0reg.h   Thu Jul 22 23:23:39 2010        
(r210397)
@@ -99,6 +99,9 @@
 #define        S3C24X0_IIS_BASE        
S3C24X0_DEV_PA_TO_VA(S3C24X0_IIS_PA_BASE)
 #define        S3C24X0_GPIO_PA_BASE    0x56000000
 #define        S3C24X0_GPIO_BASE       
S3C24X0_DEV_PA_TO_VA(S3C24X0_GPIO_PA_BASE)
+#define        S3C24X0_RTC_PA_BASE     0x57000000
+#define        S3C24X0_RTC_BASE        
S3C24X0_DEV_PA_TO_VA(S3C24X0_RTC_PA_BASE)
+#define        S3C24X0_RTC_SIZE        0x8C
 #define        S3C24X0_ADC_PA_BASE     0x58000000
 #define        S3C24X0_ADC_BASE        
S3C24X0_DEV_PA_TO_VA(S3C24X0_ADC_PA_BASE)
 #define        S3C24X0_SPI0_PA_BASE    0x59000000
@@ -642,7 +645,30 @@
 
 #define        ADCDAT_DATAMASK         0x3ff
 
-/* RTC */ /* XXX */
+/* RTC */
+#define        RTC_RTCCON              0x40
+#define         RTCCON_RTCEN           (1<<0)
+#define         RTCCON_CLKSEL          (1<<1)
+#define         RTCCON_CNTSEL          (1<<2)
+#define         RTCCON_CLKRST          (1<<3)
+#define        RTC_TICNT0              0x44
+/* TICNT1 on 2440 */
+#define        RTC_RTCALM              0x50
+#define        RTC_ALMSEC              0x54
+#define        RTC_ALMMIN              0x58
+#define        RTC_ALMHOUR             0x5C
+#define        RTC_ALMDATE             0x60
+#define        RTC_ALMMON              0x64
+#define        RTC_ALMYEAR             0x68
+/* RTCRST on 2410 */
+#define        RTC_BCDSEC              0x70
+#define        RTC_BCDMIN              0x74
+#define        RTC_BCDHOUR             0x78
+#define        RTC_BCDDATE             0x7C
+#define        RTC_BCDDAY              0x80
+#define        RTC_BCDMON              0x84
+#define        RTC_BCDYEAR             0x88
+
 
 /* SPI */
 #define        S3C24X0_SPI_SIZE        0x20
_______________________________________________
[email protected] mailing list
http://lists.freebsd.org/mailman/listinfo/svn-src-all
To unsubscribe, send any mail to "[email protected]"

Reply via email to