mirror of
https://github.com/apache/nuttx.git
synced 2026-05-22 05:42:05 +08:00
arch/xmc4 Add tickless support
This commit is contained in:
committed by
Alan Carvalho de Assis
parent
be482cd830
commit
63782c7ff2
@@ -600,6 +600,7 @@ config ARCH_CHIP_XMC4
|
||||
select ARCH_HAVE_I2CRESET
|
||||
select ARM_HAVE_MPU_UNIFIED
|
||||
select ARMV7M_HAVE_STACKCHECK
|
||||
select ARCH_HAVE_TICKLESS
|
||||
---help---
|
||||
Infineon XMC4xxx(ARM Cortex-M4) architectures
|
||||
|
||||
|
||||
@@ -25,6 +25,7 @@ include armv7-m/Make.defs
|
||||
CHIP_CSRCS = xmc4_allocateheap.c xmc4_clockconfig.c xmc4_clockutils.c
|
||||
CHIP_CSRCS += xmc4_clrpend.c xmc4_flash.c xmc4_gpio.c xmc4_irq.c
|
||||
CHIP_CSRCS += xmc4_lowputc.c xmc4_serial.c xmc4_start.c xmc4_usic.c
|
||||
CHIP_CSRCS += xmc4_ccu4.c
|
||||
|
||||
# Configuration-dependent Kinetis files
|
||||
|
||||
@@ -34,6 +35,8 @@ endif
|
||||
|
||||
ifneq ($(CONFIG_SCHED_TICKLESS),y)
|
||||
CHIP_CSRCS += xmc4_timerisr.c
|
||||
else
|
||||
CHIP_CSRCS += xmc4_tickless.c
|
||||
endif
|
||||
|
||||
ifeq ($(CONFIG_BUILD_PROTECTED),y)
|
||||
|
||||
@@ -0,0 +1,195 @@
|
||||
/****************************************************************************
|
||||
* arch/arm/src/xmc4/xmc4_ccu4.c
|
||||
*
|
||||
* Licensed to the Apache Software Foundation (ASF) under one or more
|
||||
* contributor license agreements. See the NOTICE file distributed with
|
||||
* this work for additional information regarding copyright ownership. The
|
||||
* ASF licenses this file to you under the Apache License, Version 2.0 (the
|
||||
* "License"); you may not use this file except in compliance with the
|
||||
* License. You may obtain a copy of the License at
|
||||
*
|
||||
* http://www.apache.org/licenses/LICENSE-2.0
|
||||
*
|
||||
* Unless required by applicable law or agreed to in writing, software
|
||||
* distributed under the License is distributed on an "AS IS" BASIS, WITHOUT
|
||||
* WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. See the
|
||||
* License for the specific language governing permissions and limitations
|
||||
* under the License.
|
||||
*
|
||||
****************************************************************************/
|
||||
|
||||
/****************************************************************************
|
||||
* XMC CCU Driver
|
||||
*
|
||||
* For now, this file contains only helper methods mandatory for xmc tickless
|
||||
* feature. Contibutions are welcomed.
|
||||
*
|
||||
****************************************************************************/
|
||||
|
||||
/****************************************************************************
|
||||
* Included Files
|
||||
****************************************************************************/
|
||||
|
||||
#include <nuttx/config.h>
|
||||
#include <arch/board/board.h>
|
||||
|
||||
#include <assert.h>
|
||||
#include <errno.h>
|
||||
#include <debug.h>
|
||||
|
||||
#include "arm_internal.h"
|
||||
#include "hardware/xmc4_ccu4.h"
|
||||
#include "xmc4_ccu4.h"
|
||||
|
||||
#define CCU4_NDIVIDERS 15
|
||||
|
||||
static const uint8_t g_log2divider[CCU4_NDIVIDERS] =
|
||||
{
|
||||
1, /* TIMER_CLOCK1 -> div2 */
|
||||
2, /* TIMER_CLOCK1 -> div4 */
|
||||
3, /* TIMER_CLOCK2 -> div8 */
|
||||
4, /* TIMER_CLOCK2 -> div16 */
|
||||
5, /* TIMER_CLOCK3 -> div32 */
|
||||
6, /* TIMER_CLOCK3 -> div64 */
|
||||
7, /* TIMER_CLOCK4 -> div128 */
|
||||
8, /* TIMER_CLOCK4 -> div256 */
|
||||
9, /* TIMER_CLOCK4 -> div512 */
|
||||
10, /* TIMER_CLOCK4 -> div1024 */
|
||||
11, /* TIMER_CLOCK4 -> div2048 */
|
||||
12, /* TIMER_CLOCK4 -> div4096 */
|
||||
13, /* TIMER_CLOCK4 -> div8192 */
|
||||
14, /* TIMER_CLOCK4 -> div16384 */
|
||||
15 /* TIMER_CLOCK4 -> div32769 */
|
||||
};
|
||||
|
||||
/****************************************************************************
|
||||
* Private Functions
|
||||
****************************************************************************/
|
||||
|
||||
/****************************************************************************
|
||||
* Name: xmc4_ccu4_divfreq_lookup
|
||||
*
|
||||
* Description:
|
||||
* Given the TC input frequency (Ftcin) and a divider index, return the
|
||||
* value of the divided frequency
|
||||
*
|
||||
* Input Parameters:
|
||||
* ftcin - TC input frequency
|
||||
* ndx - Divider index
|
||||
*
|
||||
* Returned Value:
|
||||
* The divided frequency value
|
||||
*
|
||||
****************************************************************************/
|
||||
|
||||
static uint32_t xmc4_ccu4_divfreq_lookup(uint32_t ftcin, int ndx)
|
||||
{
|
||||
return ftcin >> g_log2divider[ndx];
|
||||
}
|
||||
|
||||
/****************************************************************************
|
||||
* Name: xmc4_ccu4_freqdiv_lookup
|
||||
*
|
||||
* Description:
|
||||
* Given the TC input frequency (Ftcin) and a divider index, return the
|
||||
* value of the Ftcin divider.
|
||||
*
|
||||
* Input Parameters:
|
||||
* ftcin - TC input frequency
|
||||
* ndx - Divider index
|
||||
*
|
||||
* Returned Value:
|
||||
* The Ftcin input divider value
|
||||
*
|
||||
****************************************************************************/
|
||||
|
||||
static int xmc4_ccu4_freqdiv_lookup(uint32_t ftcin, int ndx)
|
||||
{
|
||||
return 1 << g_log2divider[ndx];
|
||||
}
|
||||
|
||||
/****************************************************************************
|
||||
* Public Functions
|
||||
****************************************************************************/
|
||||
|
||||
/****************************************************************************
|
||||
* Name: xmc4_ccu4_divisor
|
||||
*
|
||||
* Description:
|
||||
* Finds the best MCK divisor given the timer frequency and MCK. The
|
||||
* result is guaranteed to satisfy the following equation:
|
||||
*
|
||||
* (Ftcin / (div * 65536)) <= freq <= (Ftcin / dev)
|
||||
*
|
||||
* where:
|
||||
* freq - the desired frequency
|
||||
* Ftcin - The timer/counter input frequency
|
||||
* div - With DIV being the highest possible value.
|
||||
*
|
||||
* Input Parameters:
|
||||
* frequency Desired timer frequency.
|
||||
* div Divisor value.
|
||||
* pssiv PSSIV field value for divisor.
|
||||
*
|
||||
* Returned Value:
|
||||
* Zero (OK) if a proper divisor has been found, otherwise a negated errno
|
||||
* value indicating the nature of the failure.
|
||||
*
|
||||
****************************************************************************/
|
||||
|
||||
int xmc4_ccu4_divisor(uint32_t frequency, uint32_t *div, uint32_t *pssiv)
|
||||
{
|
||||
uint32_t ftcin = BOARD_CCU_FREQUENCY;
|
||||
int ndx = 0;
|
||||
|
||||
tmrinfo("frequency=%" PRIu32 "\n", frequency);
|
||||
|
||||
/* Satisfy lower bound. That is, the value of the divider such that:
|
||||
*
|
||||
* frequency >= (tc_input_frequency * 65536) / divider.
|
||||
*/
|
||||
|
||||
while (frequency < (xmc4_ccu4_divfreq_lookup(ftcin, ndx) >> 16))
|
||||
{
|
||||
if (++ndx > CCU4_NDIVIDERS)
|
||||
{
|
||||
/* If no divisor can be found, return -ERANGE */
|
||||
|
||||
tmrerr("ERROR: Lower bound search failed\n");
|
||||
return -ERANGE;
|
||||
}
|
||||
}
|
||||
|
||||
/* Try to maximize DIV while still satisfying upper bound. That the
|
||||
* value of the divider such that:
|
||||
*
|
||||
* frequency < tc_input_frequency / divider.
|
||||
*/
|
||||
|
||||
for (; ndx < (CCU4_NDIVIDERS - 1); ndx++)
|
||||
{
|
||||
if (frequency > xmc4_ccu4_divfreq_lookup(ftcin, ndx + 1))
|
||||
{
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
/* Return the divider value */
|
||||
|
||||
if (div)
|
||||
{
|
||||
uint32_t value = xmc4_ccu4_freqdiv_lookup(ftcin, ndx);
|
||||
tmrinfo("return div=%lu\n", (unsigned long)value);
|
||||
*div = value;
|
||||
}
|
||||
|
||||
/* Return the PSSIV selection */
|
||||
|
||||
if (pssiv)
|
||||
{
|
||||
tmrinfo("return pssiv=%d\n", ndx + 1);
|
||||
*pssiv = ndx + 1;
|
||||
}
|
||||
|
||||
return OK;
|
||||
}
|
||||
@@ -0,0 +1,64 @@
|
||||
/****************************************************************************
|
||||
* arch/arm/src/xmc4/xmc4_ccu4.h
|
||||
*
|
||||
* Licensed to the Apache Software Foundation (ASF) under one or more
|
||||
* contributor license agreements. See the NOTICE file distributed with
|
||||
* this work for additional information regarding copyright ownership. The
|
||||
* ASF licenses this file to you under the Apache License, Version 2.0 (the
|
||||
* "License"); you may not use this file except in compliance with the
|
||||
* License. You may obtain a copy of the License at
|
||||
*
|
||||
* http://www.apache.org/licenses/LICENSE-2.0
|
||||
*
|
||||
* Unless required by applicable law or agreed to in writing, software
|
||||
* distributed under the License is distributed on an "AS IS" BASIS, WITHOUT
|
||||
* WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. See the
|
||||
* License for the specific language governing permissions and limitations
|
||||
* under the License.
|
||||
*
|
||||
****************************************************************************/
|
||||
|
||||
#ifndef __ARCH_ARM_SRC_XMC4_XMC4_CCU4_H
|
||||
#define __ARCH_ARM_SRC_XMC4_XMC4_CCU4_H
|
||||
|
||||
/****************************************************************************
|
||||
* Included Files
|
||||
****************************************************************************/
|
||||
|
||||
#include <nuttx/config.h>
|
||||
|
||||
#include <stdint.h>
|
||||
#include <stdbool.h>
|
||||
|
||||
/****************************************************************************
|
||||
* Public Functions Prototypes
|
||||
****************************************************************************/
|
||||
|
||||
/****************************************************************************
|
||||
* Name: xmc4_ccu4_divisor
|
||||
*
|
||||
* Description:
|
||||
* Finds the best MCK divisor given the timer frequency and MCK. The
|
||||
* result is guaranteed to satisfy the following equation:
|
||||
*
|
||||
* (Ftcin / (div * 65536)) <= freq <= (Ftcin / dev)
|
||||
*
|
||||
* where:
|
||||
* freq - the desired frequency
|
||||
* Ftcin - The timer/counter input frequency
|
||||
* div - With DIV being the highest possible value.
|
||||
*
|
||||
* Input Parameters:
|
||||
* frequency Desired timer frequency.
|
||||
* div Divisor value.
|
||||
* pssiv PSSIV field value for divisor.
|
||||
*
|
||||
* Returned Value:
|
||||
* Zero (OK) if a proper divisor has been found, otherwise a negated errno
|
||||
* value indicating the nature of the failure.
|
||||
*
|
||||
****************************************************************************/
|
||||
|
||||
int xmc4_ccu4_divisor(uint32_t frequency, uint32_t *div, uint32_t *pssiv);
|
||||
|
||||
#endif
|
||||
File diff suppressed because it is too large
Load Diff
Reference in New Issue
Block a user