[PATCH 5/8] generic_or1k BSP clock driver correction

Hesham Almatary heshamelmatary at gmail.com
Sat Feb 27 18:57:52 UTC 2016


On Sat, Feb 20, 2016 at 11:01 PM,  <jakob.viketoft at gmail.com> wrote:
> From: Jakob Viketoft <jakob.viketoft at aacmicrotec.com>
>
>  - Improve the clock driver to use RTEMS default tick period
>    or the on the one supplied by the application
>  - Avoid rewriting the timer settings, since all we need is to clear the interrupt
>  - Remove any mention of or1ksim in favour of generic_or1k
>
> Close #2600
> ---
>  .../lib/libbsp/or1k/generic_or1k/clock/clockdrv.c  | 109 ++++++++++-----------
>  1 file changed, 51 insertions(+), 58 deletions(-)
>
> diff --git a/c/src/lib/libbsp/or1k/generic_or1k/clock/clockdrv.c b/c/src/lib/libbsp/or1k/generic_or1k/clock/clockdrv.c
> index e01d2e5..60eec98 100644
> --- a/c/src/lib/libbsp/or1k/generic_or1k/clock/clockdrv.c
> +++ b/c/src/lib/libbsp/or1k/generic_or1k/clock/clockdrv.c
> @@ -3,13 +3,15 @@
>   *
>   * @ingroup bsp_clock
>   *
> - * @brief or1k clock support.
> + * @brief generic_or1k clock support.
>   */
>
>  /*
>   * generic_or1k Clock driver
>   *
>   * COPYRIGHT (c) 2014-2015 Hesham ALMatary <heshamelmatary at gmail.com>
> + * Copyright (c) 2014-2016 ÅAC Microtec AB <www.aacmicrotec.com>
> + *                         Jakob Viketoft <jakob.viketoft at aacmicrotec.com>
>   *
>   * The license and distribution terms for this file may be
>   * found in the file LICENSE in this distribution or at
> @@ -25,35 +27,30 @@
>  #include <rtems/timecounter.h>
>
>  /* The number of clock cycles before generating a tick timer interrupt. */
> -#define TTMR_NUM_OF_CLOCK_TICKS_INTERRUPT     0x09ED9
> -#define OR1K_CLOCK_CYCLE_TIME_NANOSECONDS     10
> +#define OR1K_CLOCK_CYCLE_TIME_NANOSECONDS     (1000000000 / OR1K_BSP_CLOCK_FREQ)
clockdrv.c:30:61: error: 'OR1K_BSP_CLOCK_FREQ' undeclared (first use
in this function)

>
> -static struct timecounter or1ksim_tc;
> -
> -/* CPU counter */
> +static struct timecounter generic_or1k_tc;
>  static CPU_Counter_ticks cpu_counter_ticks;
> +static uint32_t timer_counts_per_clock_tick;
>
> -/* This prototype is added here to Avoid warnings */
> +/* These prototypes are added here to avoid warnings */
>  void Clock_isr(void *arg);
> +static uint32_t generic_or1k_get_timecount(struct timecounter *tc);
>
>  static void generic_or1k_clock_at_tick(void)
>  {
> -  uint32_t TTMR;
> +  uint32_t ttmr;
>
> - /* For TTMR register,
> -  * The least significant 28 bits are the number of clock cycles
> -  * before generating a tick timer interrupt. While the most
> -  * significant 4 bits are used for mode configuration, tick timer
> -  * interrupt enable and pending interrupts status.
> -  */
> -  TTMR = (CPU_OR1K_SPR_TTMR_MODE_RESTART | CPU_OR1K_SPR_TTMR_IE |
> -           (TTMR_NUM_OF_CLOCK_TICKS_INTERRUPT & CPU_OR1K_SPR_TTMR_TP_MASK)
> -         ) & ~(CPU_OR1K_SPR_TTMR_IP);
> +  /* Get TTMR value */
> +  ttmr = _OR1K_mfspr(CPU_OR1K_SPR_TTMR);
>
> -  _OR1K_mtspr(CPU_OR1K_SPR_TTMR, TTMR);
> -  _OR1K_mtspr(CPU_OR1K_SPR_TTCR, 0);
> +  /* Clear interrupt */
> +  ttmr &=  ~(CPU_OR1K_SPR_TTMR_IP);
>
> -  cpu_counter_ticks += TTMR_NUM_OF_CLOCK_TICKS_INTERRUPT;
> +  /* Write it back */
> +  _OR1K_mtspr(CPU_OR1K_SPR_TTMR, ttmr);
> +
> +  cpu_counter_ticks += timer_counts_per_clock_tick;
>  }
>
>  static void generic_or1k_clock_handler_install(
> @@ -61,35 +58,19 @@ static void generic_or1k_clock_handler_install(
>     proc_ptr old_isr
>  )
>  {
> -  rtems_status_code sc = RTEMS_SUCCESSFUL;
>    old_isr = NULL;
>    _CPU_ISR_install_vector(OR1K_EXCEPTION_TICK_TIMER,
>                            new_isr,
>                            old_isr);
> -
> -  if (sc != RTEMS_SUCCESSFUL) {
> -    rtems_fatal_error_occurred(0xdeadbeef);
> -  }
> -}
> -
> -static uint32_t or1ksim_get_timecount(struct timecounter *tc)
> -{
> -  uint32_t ticks_since_last_timer_interrupt;
> -
> -  ticks_since_last_timer_interrupt = _OR1K_mfspr(CPU_OR1K_SPR_TTCR);
> -
> -  return cpu_counter_ticks + ticks_since_last_timer_interrupt;
> -}
> -
> -CPU_Counter_ticks _CPU_Counter_read(void)
> -{
> -  return or1ksim_get_timecount(NULL);
>  }
>
>  static void generic_or1k_clock_initialize(void)
>  {
> -  uint64_t frequency = (1000000000 / OR1K_CLOCK_CYCLE_TIME_NANOSECONDS);
> -  uint32_t TTMR;
> +  uint32_t ttmr;
> +
> +  /* Calculate timer value for given time per clock tick */
> +  timer_counts_per_clock_tick = (1000 * rtems_configuration_get_microseconds_per_tick()) /
> +    OR1K_CLOCK_CYCLE_TIME_NANOSECONDS;
>
>   /* For TTMR register,
>    * The least significant 28 bits are the number of clock cycles
> @@ -97,40 +78,52 @@ static void generic_or1k_clock_initialize(void)
>    * significant 4 bits are used for mode configuration, tick timer
>    * interrupt enable and pending interrupts status.
>    */
> +  ttmr = (CPU_OR1K_SPR_TTMR_MODE_RESTART | CPU_OR1K_SPR_TTMR_IE |
> +          (timer_counts_per_clock_tick & CPU_OR1K_SPR_TTMR_TP_MASK)) &
> +    ~(CPU_OR1K_SPR_TTMR_IP);
>
> -  /* FIXME: Long interval should pass since initializing the tick timer
> -   * registers fires exceptions dispite interrupts has not been enabled yet.
> -   */
> -  TTMR = (CPU_OR1K_SPR_TTMR_MODE_RESTART | CPU_OR1K_SPR_TTMR_IE |
> -           (0xFFED9 & CPU_OR1K_SPR_TTMR_TP_MASK)
> -         ) & ~(CPU_OR1K_SPR_TTMR_IP);
> -
> -  _OR1K_mtspr(CPU_OR1K_SPR_TTMR, TTMR);
> +  _OR1K_mtspr(CPU_OR1K_SPR_TTMR, ttmr);
>    _OR1K_mtspr(CPU_OR1K_SPR_TTCR, 0);
>
> +  /* Initialize CPU Counter */
> +  cpu_counter_ticks = 0;
> +
>    /* Initialize timecounter */
> -  or1ksim_tc.tc_get_timecount = or1ksim_get_timecount;
> -  or1ksim_tc.tc_counter_mask = 0xffffffff;
> -  or1ksim_tc.tc_frequency = frequency;
> -  or1ksim_tc.tc_quality = RTEMS_TIMECOUNTER_QUALITY_CLOCK_DRIVER;
> -  rtems_timecounter_install(&or1ksim_tc);
> +  generic_or1k_tc.tc_get_timecount = generic_or1k_get_timecount;
> +  generic_or1k_tc.tc_counter_mask = 0xffffffff;
> +  generic_or1k_tc.tc_frequency = OR1K_BSP_CLOCK_FREQ;
> +  generic_or1k_tc.tc_quality = RTEMS_TIMECOUNTER_QUALITY_CLOCK_DRIVER;
> +  rtems_timecounter_install(&generic_or1k_tc);
>  }
>
>  static void generic_or1k_clock_cleanup(void)
>  {
> - uint32_t sr;
> +  uint32_t sr;
>
>    sr = _OR1K_mfspr(CPU_OR1K_SPR_SR);
>
>    /* Disable tick timer exceptions */
> -  _OR1K_mtspr(CPU_OR1K_SPR_SR, (sr & ~CPU_OR1K_SPR_SR_IEE)
> -  & ~CPU_OR1K_SPR_SR_TEE);
> +  _OR1K_mtspr(CPU_OR1K_SPR_SR, sr & ~CPU_OR1K_SPR_SR_TEE);
>
>    /* Invalidate tick timer config registers */
>    _OR1K_mtspr(CPU_OR1K_SPR_TTCR, 0);
>    _OR1K_mtspr(CPU_OR1K_SPR_TTMR, 0);
>  }
>
> +static uint32_t generic_or1k_get_timecount(struct timecounter *tc)
> +{
> +  uint32_t counts_since_last_timer_interrupt;
> +
> +  counts_since_last_timer_interrupt = _OR1K_mfspr(CPU_OR1K_SPR_TTCR);
> +
> +  return cpu_counter_ticks + counts_since_last_timer_interrupt;
> +}
> +
> +CPU_Counter_ticks _CPU_Counter_read(void)
> +{
> +  return generic_or1k_get_timecount(NULL);
> +}
> +
>  CPU_Counter_ticks _CPU_Counter_difference(
>    CPU_Counter_ticks second,
>    CPU_Counter_ticks first
> @@ -146,7 +139,7 @@ CPU_Counter_ticks _CPU_Counter_difference(
>  #define Clock_driver_support_install_isr(isr, old_isr) \
>    do {                                                 \
>      old_isr = NULL;                                    \
> -    generic_or1k_clock_handler_install(isr, old_isr);       \
> +    generic_or1k_clock_handler_install(isr, old_isr);  \
>    } while (0)
>
>  #define Clock_driver_support_shutdown_hardware() generic_or1k_clock_cleanup()
> --
> 2.1.4
>
> _______________________________________________
> devel mailing list
> devel at rtems.org
> http://lists.rtems.org/mailman/listinfo/devel



-- 
Hesham



More information about the devel mailing list