ostimer_s3c4510b.c

Go to the documentation of this file.
00001 /*
00002  * Copyright (C) 2001-2004 by egnite Software GmbH. All rights reserved.
00003  *
00004  * Redistribution and use in source and binary forms, with or without
00005  * modification, are permitted provided that the following conditions
00006  * are met:
00007  *
00008  * 1. Redistributions of source code must retain the above copyright
00009  *    notice, this list of conditions and the following disclaimer.
00010  * 2. Redistributions in binary form must reproduce the above copyright
00011  *    notice, this list of conditions and the following disclaimer in the
00012  *    documentation and/or other materials provided with the distribution.
00013  * 3. Neither the name of the copyright holders nor the names of
00014  *    contributors may be used to endorse or promote products derived
00015  *    from this software without specific prior written permission.
00016  *
00017  * THIS SOFTWARE IS PROVIDED BY EGNITE SOFTWARE GMBH AND CONTRIBUTORS
00018  * ``AS IS'' AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
00019  * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS
00020  * FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL EGNITE
00021  * SOFTWARE GMBH OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT,
00022  * INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING,
00023  * BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS
00024  * OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED
00025  * AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY,
00026  * OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF
00027  * THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
00028  * SUCH DAMAGE.
00029  *
00030  * For additional information see http://www.ethernut.de/
00031  *
00032  */
00033 
00034 /*
00035  * $Log: ostimer_s3c4510b.c,v $
00036  * Revision 1.4  2007/08/17 10:44:37  haraldkipp
00037  * Timer enable/disable macro replaces previous global interrupt
00038  * enable/disable or function calling.
00039  *
00040  * Revision 1.3  2006/10/08 16:48:07  haraldkipp
00041  * Documentation fixed
00042  *
00043  * Revision 1.2  2005/10/24 08:58:48  haraldkipp
00044  * Header file moved.
00045  *
00046  * Revision 1.1  2005/07/26 18:02:26  haraldkipp
00047  * Moved from dev.
00048  *
00049  * Revision 1.2  2005/07/20 09:17:26  haraldkipp
00050  * Default NUT_CPU_FREQ and NUT_TICK_FREQ added.
00051  * NutTimerIntr() removed, because we can use the hardware independent code.
00052  *
00053  * Revision 1.1  2005/05/27 17:16:40  drsung
00054  * Moved the file.
00055  *
00056  * Revision 1.5  2005/04/05 17:50:46  haraldkipp
00057  * Use register names in gba.h.
00058  *
00059  * Revision 1.4  2004/11/08 19:16:37  haraldkipp
00060  * Hacked in Gameboy timer support
00061  *
00062  * Revision 1.3  2004/10/03 18:42:21  haraldkipp
00063  * No GBA support yet, but let the compiler run through
00064  *
00065  * Revision 1.2  2004/09/08 10:19:39  haraldkipp
00066  * Running on AT91 and S3C, thanks to James Tyou
00067  *
00068  */
00069 
00070 #include <cfg/arch.h>
00071 #if defined(MCU_AT91R40008)
00072 #include <arch/arm/at91.h>
00073 
00074 #elif defined(MCU_S3C4510B)
00075 #include <arch/arm.h>
00076 #include <dev/s3c4510b_hw.h>
00077 #include <dev/s3c4510b_irqs.h>
00078 
00079 #elif defined(MCU_GBA)
00080 #include <arch/gba.h>
00081 #include <dev/irqreg.h>
00082 
00083 #endif
00084 
00085 #ifndef NUT_CPU_FREQ
00086 #define NUT_CPU_FREQ    1000000UL
00087 #endif
00088 
00089 #ifndef NUT_TICK_FREQ
00090 #define NUT_TICK_FREQ   1000UL
00091 #endif
00092 
00093 #if defined(MCU_AT91R40008)
00094 static int dummy;
00095 #endif
00096 
00097 static void (*os_handler) (void *);
00098 
00112 void NutDelay(u_char ms)
00113 {
00114     u_short delay_cnt = 2400;   //*KU* for 14.745600 MHz Clock
00115     u_short delay_cnt_buffer;
00116 
00117     while (ms--) {
00118         delay_cnt_buffer = delay_cnt;
00119         while (delay_cnt_buffer--);
00120     }
00121 }
00122 
00123 
00127 #if defined(MCU_AT91R40008)
00128 void Timer0Entry(void) __attribute__ ((naked));
00129 void Timer0Entry(void)
00130 {
00131     IRQ_ENTRY();
00132     dummy = inr(TC0_SR);
00133     os_handler(0);
00134     IRQ_EXIT();
00135 }
00136 
00137 #elif defined(MCU_GBA)
00138 
00139 void Timer3Entry(void *arg)
00140 {
00141     outw(REG_IF, INT_TMR3);
00142     os_handler(0);
00143 }
00144 
00145 #endif
00146 
00158 void NutRegisterTimer(void (*handler) (void *))
00159 {
00160     os_handler = handler;
00161 
00162 #if defined(MCU_AT91R40008)
00163 
00164     /* Disable the Clock Counter */
00165     outr(TC0_CCR, TC_CLKDIS);
00166     /* Disable all interrupts */
00167     outr(TC0_IDR, 0xFFFFFFFF);
00168     /* Clear the status register. */
00169     dummy = inr(TC0_SR);
00170     /* Select divider and compare trigger */
00171     outr(TC0_CMR, TC_CLKS_MCK32 | TC_CPCTRG);
00172     /* Enable the Clock counter */
00173     outr(TC0_CCR, TC_CLKEN);
00174     /* Validate the RC compare interrupt */
00175     outr(TC0_IER, TC_CPCS);
00176 
00177     /* Disable timer 0 interrupts. */
00178     outr(AIC_IDCR, _BV(TC0_ID));
00179     /* Set the TC0 IRQ handler address */
00180     outr(AIC_SVR(4), (unsigned int)Timer0Entry);
00181     /* Set the trigg and priority for timer 0 interrupt */
00182     /* Level 7 is highest, level 0 lowest. */
00183     outr(AIC_SMR(4), (AIC_SRCTYPE_INT_LEVEL_SENSITIVE | 0x4));
00184     /* Clear timer 0 interrupt */
00185     outr(AIC_ICCR, _BV(TC0_ID));
00186     /* Enable timer 0 interrupts */
00187     outr(AIC_IECR, _BV(TC0_ID));
00188 
00189     /* Set compare value for 1 ms. */
00190     outr(TC0_RC, 0x80F);
00191     /* Software trigger starts the clock. */
00192     outr(TC0_CCR, TC_SWTRG);
00193 
00194 #elif defined(MCU_S3C4510B)
00195 
00196     INT_DISABLE(IRQ_TIMER);
00197     CSR_WRITE(TCNT0, 0);
00198     CSR_WRITE(TDATA0, CLOCK_TICK_RATE);
00199     CSR_WRITE(TMOD, TMOD_TIMER0_VAL);
00200 
00201     CLEAR_PEND_INT(IRQ_TIMER);
00202 
00203     NutRegisterIrqHandler(
00204         &InterruptHandlers[IRQ_TIMER], handler, 0);
00205 
00206     INT_ENABLE(IRQ_TIMER);
00207 
00208 #elif defined(MCU_GBA)
00209 
00210     /* Disable master interrupt. */
00211     outw(REG_IME, 0);
00212 
00213     /* Set global interrupt vector. */
00214     NutRegisterIrqHandler(&sig_TMR3, Timer3Entry, 0);
00215 
00216     /* Enable timer and timer interrupts. */
00217     outdw(REG_TMR3CNT, TMR_IRQ_ENA | TMR_ENA | 48756);
00218 
00219     /* Enable timer 3 interrupts. */
00220     outw(REG_IE, inw(REG_IE) | INT_TMR3);
00221 
00222     /* Enable master interrupt. */
00223     outw(REG_IME, 1);
00224 
00225 #else
00226 #warning "MCU not defined"
00227 #endif
00228 }
00229 
00235 u_long NutGetCpuClock(void)
00236 {
00237     return NUT_CPU_FREQ;
00238 }
00239 
00245 u_long NutGetTickClock(void)
00246 {
00247     return NUT_TICK_FREQ;
00248 }
00249 
00253 u_long NutTimerMillisToTicks(u_long ms)
00254 {
00255     return ms * 1000L / NutGetTickClock();
00256 }
00257 
00258 

© 2000-2007 by egnite Software GmbH - visit http://www.ethernut.de/