From owner-svn-soc-all@FreeBSD.ORG Sat Jun 2 13:22:32 2012 Return-Path: Delivered-To: svn-soc-all@FreeBSD.org Received: from socsvn.FreeBSD.org (unknown [IPv6:2001:4f8:fff6::2f]) by hub.freebsd.org (Postfix) with SMTP id 859661065672 for ; Sat, 2 Jun 2012 13:22:30 +0000 (UTC) (envelope-from aleek@FreeBSD.org) Received: by socsvn.FreeBSD.org (sSMTP sendmail emulation); Sat, 02 Jun 2012 13:22:30 +0000 Date: Sat, 02 Jun 2012 13:22:30 +0000 From: aleek@FreeBSD.org To: svn-soc-all@FreeBSD.org MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit Message-Id: <20120602132230.859661065672@hub.freebsd.org> Cc: Subject: socsvn commit: r236934 - in soc2012/aleek/beaglexm-armv6/sys/arm/ti: am37x omap3 X-BeenThere: svn-soc-all@freebsd.org X-Mailman-Version: 2.1.5 Precedence: list List-Id: SVN commit messages for the entire Summer of Code repository List-Unsubscribe: , List-Archive: List-Post: List-Help: List-Subscribe: , X-List-Received-Date: Sat, 02 Jun 2012 13:22:32 -0000 Author: aleek Date: Sat Jun 2 13:22:29 2012 New Revision: 236934 URL: http://svnweb.FreeBSD.org/socsvn/?view=rev&rev=236934 Log: importing general purpose timer code for omap35x and am37x ti arm Added: soc2012/aleek/beaglexm-armv6/sys/arm/ti/omap3/omap3_intr.c Modified: soc2012/aleek/beaglexm-armv6/sys/arm/ti/am37x/am37x_gptimer.c soc2012/aleek/beaglexm-armv6/sys/arm/ti/am37x/am37x_timer.c soc2012/aleek/beaglexm-armv6/sys/arm/ti/am37x/std.am37x soc2012/aleek/beaglexm-armv6/sys/arm/ti/omap3/files.omap3 Modified: soc2012/aleek/beaglexm-armv6/sys/arm/ti/am37x/am37x_gptimer.c ============================================================================== --- soc2012/aleek/beaglexm-armv6/sys/arm/ti/am37x/am37x_gptimer.c Sat Jun 2 12:26:14 2012 (r236933) +++ soc2012/aleek/beaglexm-armv6/sys/arm/ti/am37x/am37x_gptimer.c Sat Jun 2 13:22:29 2012 (r236934) @@ -23,6 +23,8 @@ * 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. + * + * gptimers are exact the same in am37x and omap35x */ #include Modified: soc2012/aleek/beaglexm-armv6/sys/arm/ti/am37x/am37x_timer.c ============================================================================== --- soc2012/aleek/beaglexm-armv6/sys/arm/ti/am37x/am37x_timer.c Sat Jun 2 12:26:14 2012 (r236933) +++ soc2012/aleek/beaglexm-armv6/sys/arm/ti/am37x/am37x_timer.c Sat Jun 2 13:22:29 2012 (r236934) @@ -59,10 +59,10 @@ #include #include -#include +#include #include -#include +#include #include //#define CPU_CLOCKSPEED 500000000 @@ -255,7 +255,7 @@ tc_init(&g_omap3_timecounter); /* Calibrate the delay loop */ - omap3_calibrate_delay_loop(&g_omap3_timecounter); + //omap3_calibrate_delay_loop(&g_omap3_timecounter); /* Restore interrupt state */ restore_interrupts(oldirqstate); @@ -272,6 +272,7 @@ * RETURNS: * nothing */ +#if 0 void DELAY(int usec) { @@ -283,8 +284,8 @@ } } +#endif -#if 0 void DELAY(int n) { @@ -346,9 +347,8 @@ first = last; } } -#endif - +#if 0 /** * cpu_startprofclock - Starts the profile clock * @@ -375,3 +375,4 @@ { /* TODO: implement */ } +#endif Modified: soc2012/aleek/beaglexm-armv6/sys/arm/ti/am37x/std.am37x ============================================================================== --- soc2012/aleek/beaglexm-armv6/sys/arm/ti/am37x/std.am37x Sat Jun 2 12:26:14 2012 (r236933) +++ soc2012/aleek/beaglexm-armv6/sys/arm/ti/am37x/std.am37x Sat Jun 2 13:22:29 2012 (r236934) @@ -1,6 +1,7 @@ # Omap3 generic configuration #$FreeBSD$ files "../ti/am37x/files.am37x" +files "../ti/omap3/files.omap3" include "../ti/std.ti" makeoption ARM_LITTLE_ENDIAN Modified: soc2012/aleek/beaglexm-armv6/sys/arm/ti/omap3/files.omap3 ============================================================================== --- soc2012/aleek/beaglexm-armv6/sys/arm/ti/omap3/files.omap3 Sat Jun 2 12:26:14 2012 (r236933) +++ soc2012/aleek/beaglexm-armv6/sys/arm/ti/omap3/files.omap3 Sat Jun 2 13:22:29 2012 (r236934) @@ -1,3 +1,3 @@ #$FreeBSD$ -arm/ti/omap3/omap3_timer.c standard +arm/ti/omap3/omap3_intr.c standard Added: soc2012/aleek/beaglexm-armv6/sys/arm/ti/omap3/omap3_intr.c ============================================================================== --- /dev/null 00:00:00 1970 (empty, because file is newly added) +++ soc2012/aleek/beaglexm-armv6/sys/arm/ti/omap3/omap3_intr.c Sat Jun 2 13:22:29 2012 (r236934) @@ -0,0 +1,233 @@ +/*- + * Copyright (c) 2011 + * Ben Gray . + * 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 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 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 +__FBSDID("$FreeBSD$"); + +#include +#include +#include +#include +#include + +#include +#include + + + +/* + * There are a number of ways that interrupt handling is implemented in + * the various ARM platforms, the PXA has the neatest way, it creates another + * device driver that handles everything. However IMO this is rather heavy- + * weight for playing with IRQs which should be quite fast ... so I've + * gone for something similar to the IXP425, which just directly plays with + * registers. This assumes that the interrupt control registers are already + * mapped in virtual memory at a fixed virtual address ... simplies. + * + * The intcps (OMAP3 interrupt controller) has some nice registers, were + * you write a bit to clear or set the mask register ... I think in theory + * that means that you don't need to disable interrupts while doing this, + * because it is an atomic operation. + * + * TODO: check this. + * + */ + +//these registers are the same for am37x - aleek + +#define INTCPS_SYSCONFIG 0x10 +#define INTCPS_SYSSTATUS 0x14 +#define INTCPS_SIR_IRQ 0x40 +#define INTCPS_SIR_FIQ 0x44 +#define INTCPS_CONTROL 0x48 +#define INTCPS_PROTECTION 0x4C +#define INTCPS_IDLE 0x50 +#define INTCPS_IRQ_PRIORITY 0x60 +#define INTCPS_FIQ_PRIORITY 0x64 +#define INTCPS_THRESHOLD 0x68 +#define INTCPS_ITR(n) (0x80 + (0x20 * (n))) +#define INTCPS_MIR(n) (0x84 + (0x20 * (n))) +#define INTCPS_MIR_CLEAR(n) (0x88 + (0x20 * (n))) +#define INTCPS_MIR_SET(n) (0x8C + (0x20 * (n))) +#define INTCPS_ISR_SET(n) (0x90 + (0x20 * (n))) +#define INTCPS_ISR_CLEAR(n) (0x94 + (0x20 * (n))) +#define INTCPS_PENDING_IRQ(n) (0x98 + (0x20 * (n))) +#define INTCPS_PENDING_FIQ(n) (0x9C + (0x20 * (n))) +#define INTCPS_ILR(m) (0x100 + (0x4 * (m))) + + + + +/** + * omap3_post_filter_intr - called after the IRQ has been filtered + * @arg: the IRQ number + * + * Called after the interrupt handler has done it's stuff, can be used to + * clean up interrupts that haven't been handled properly. + * + * + * RETURNS: + * nothing + */ +void +omap3_post_filter_intr(void *arg) +{ + /* uintptr_t irq = (uintptr_t) arg; */ + + /* data synchronization barrier */ + cpu_drain_writebuf(); +} + + + + + +/** + * arm_mask_irq - masks an IRQ (disables it) + * @nb: the number of the IRQ to mask (disable) + * + * Disables the interrupt at the HW level. + * + * + * RETURNS: + * nothing + */ +void +arm_mask_irq(uintptr_t nb) +{ + bus_space_write_4(g_omap3_softc->sc_iotag, g_omap3_softc->sc_intcps_ioh, + INTCPS_MIR_SET(nb >> 5), 1UL << (nb & 0x1F)); +} + + +/** + * arm_unmask_irq - unmasks an IRQ (enables it) + * @nb: the number of the IRQ to unmask (enable) + * + * Enables the interrupt at the HW level. + * + * + * RETURNS: + * nothing + */ +void +arm_unmask_irq(uintptr_t nb) +{ + // printf("[BRG] unmasking IRQ %d (off %d, bit %d)\n", nb, (nb >> 5), (nb & 0x1F)); + + bus_space_write_4(g_omap3_softc->sc_iotag, g_omap3_softc->sc_intcps_ioh, + INTCPS_MIR_CLEAR(nb >> 5), 1UL << (nb & 0x1F)); +} + + + +/** + * arm_get_next_irq - gets the next tripped interrupt + * @last_irq: the number of the last IRQ processed + * + * Enables the interrupt at the HW level. + * + * + * RETURNS: + * nothing + */ +int +arm_get_next_irq(int last_irq) +{ + uint32_t active_irq; + + /* clean-up the last IRQ */ + if (last_irq != -1) { + + /* clear the interrupt status flag */ + bus_space_write_4(g_omap3_softc->sc_iotag, g_omap3_softc->sc_intcps_ioh, + INTCPS_ISR_CLEAR(last_irq >> 5), + 1UL << (last_irq & 0x1F)); + + /* tell the interrupt logic we've dealt with the interrupt */ + bus_space_write_4(g_omap3_softc->sc_iotag, g_omap3_softc->sc_intcps_ioh, + INTCPS_CONTROL, 1); + } + + /* Get the next active interrupt */ + active_irq = bus_space_read_4(g_omap3_softc->sc_iotag, + g_omap3_softc->sc_intcps_ioh, INTCPS_SIR_IRQ); + + /* Check for spurious interrupt */ + if ((active_irq & 0xffffff80) == 0xffffff80) { + device_printf(g_omap3_softc->sc_dev, "Spurious interrupt detected " + "(0x%08x)\n", active_irq); + return -1; + } + + /* Just get the active IRQ part */ + active_irq &= 0x7F; + + /* Return the new IRQ if it is different from the previous */ + if (active_irq != last_irq) + return active_irq; + else + return -1; +} + + +/** + * omap3_setup_intr_controller - configures and enables the OMAP3 interrupt + * controller (INTCPS) + * + * + * + * RETURNS: + * nothing + */ +int +omap3_setup_intr_controller(struct omap3_softc *sc, const const int *irqs) +{ + uint32_t syscfg; + uint32_t i; + + if (sc != g_omap3_softc) + panic("Invalid omap3 soft context\n"); + + + /* Reset the interrupt controller */ + bus_space_write_4(g_omap3_softc->sc_iotag, g_omap3_softc->sc_intcps_ioh, + INTCPS_SYSCONFIG, 0x2); + + /* Loop a number of times to check if the INTCPS has come out of reset */ + for (i = 0; i < 10000; i++) { + syscfg = bus_space_read_4(g_omap3_softc->sc_iotag, + g_omap3_softc->sc_intcps_ioh, INTCPS_SYSCONFIG); + if (syscfg & 0x1UL) + break; + } + + + + return 0; +} +