forked from Imagelibrary/rtems
bsps/imxrt: Get clock for IMXRT11xx in drivers
The mcux_sdk has a different interface for getting the clock for IMXRT11xx than for getting it in IMXRT10xx. Adapt simple drivers to support that interface.
This commit is contained in:
@@ -53,6 +53,7 @@ typedef struct {
|
|||||||
volatile LPUART_Type *regs;
|
volatile LPUART_Type *regs;
|
||||||
rtems_vector_number irq;
|
rtems_vector_number irq;
|
||||||
const char *path;
|
const char *path;
|
||||||
|
clock_ip_name_t clock_ip;
|
||||||
uint32_t src_clock_hz;
|
uint32_t src_clock_hz;
|
||||||
lpuart_config_t config;
|
lpuart_config_t config;
|
||||||
} imxrt_lpuart_context;
|
} imxrt_lpuart_context;
|
||||||
@@ -174,12 +175,15 @@ static bool imxrt_lpuart_set_attributes(
|
|||||||
return true;
|
return true;
|
||||||
}
|
}
|
||||||
|
|
||||||
static uint32_t imxrt_lpuart_get_src_freq(void)
|
static uint32_t imxrt_lpuart_get_src_freq(clock_ip_name_t clock_ip)
|
||||||
{
|
{
|
||||||
uint32_t freq;
|
uint32_t freq;
|
||||||
|
#if IMXRT_IS_MIMXRT10xx
|
||||||
uint32_t mux;
|
uint32_t mux;
|
||||||
uint32_t divider;
|
uint32_t divider;
|
||||||
|
|
||||||
|
(void) clock_ip; /* Not necessary for i.MXRT1050 */
|
||||||
|
|
||||||
mux = CLOCK_GetMux(kCLOCK_UartMux);
|
mux = CLOCK_GetMux(kCLOCK_UartMux);
|
||||||
divider = 1;
|
divider = 1;
|
||||||
|
|
||||||
@@ -197,10 +201,36 @@ static uint32_t imxrt_lpuart_get_src_freq(void)
|
|||||||
|
|
||||||
divider *= CLOCK_GetDiv(kCLOCK_UartDiv) + 1U;
|
divider *= CLOCK_GetDiv(kCLOCK_UartDiv) + 1U;
|
||||||
freq /= divider;
|
freq /= divider;
|
||||||
|
#elif IMXRT_IS_MIMXRT11xx
|
||||||
|
/*
|
||||||
|
* FIXME: A future version of the mcux_sdk might provide a better method to
|
||||||
|
* get the clock instead of this hack.
|
||||||
|
*/
|
||||||
|
clock_root_t clock_root = clock_ip + kCLOCK_Root_Lpuart1 - kCLOCK_Lpuart1;
|
||||||
|
|
||||||
|
freq = CLOCK_GetRootClockFreq(clock_root);
|
||||||
|
#else
|
||||||
|
#error Getting UART clock frequency is not implemented for this chip
|
||||||
|
#endif
|
||||||
|
|
||||||
return freq;
|
return freq;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
static clock_ip_name_t imxrt_lpuart_clock_ip(volatile LPUART_Type *regs)
|
||||||
|
{
|
||||||
|
LPUART_Type *const base_addresses[] = LPUART_BASE_PTRS;
|
||||||
|
static const clock_ip_name_t lpuart_clocks[] = LPUART_CLOCKS;
|
||||||
|
size_t i;
|
||||||
|
|
||||||
|
for (i = 0; i < RTEMS_ARRAY_SIZE(base_addresses); ++i) {
|
||||||
|
if (base_addresses[i] == regs) {
|
||||||
|
return lpuart_clocks[i];
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
return kCLOCK_IpInvalid;
|
||||||
|
}
|
||||||
|
|
||||||
static void imxrt_lpuart_init_hardware(imxrt_lpuart_context *ctx)
|
static void imxrt_lpuart_init_hardware(imxrt_lpuart_context *ctx)
|
||||||
{
|
{
|
||||||
(void) LPUART_Init((LPUART_Type *)ctx->regs, &ctx->config,
|
(void) LPUART_Init((LPUART_Type *)ctx->regs, &ctx->config,
|
||||||
@@ -378,7 +408,8 @@ static void imxrt_lpuart_init_context_from_fdt(
|
|||||||
bsp_fatal(IMXRT_FATAL_LPI2C_INVALID_FDT);
|
bsp_fatal(IMXRT_FATAL_LPI2C_INVALID_FDT);
|
||||||
}
|
}
|
||||||
|
|
||||||
ctx->src_clock_hz = imxrt_lpuart_get_src_freq();
|
ctx->clock_ip = imxrt_lpuart_clock_ip(ctx->regs);
|
||||||
|
ctx->src_clock_hz = imxrt_lpuart_get_src_freq(ctx->clock_ip);
|
||||||
|
|
||||||
LPUART_GetDefaultConfig(&ctx->config);
|
LPUART_GetDefaultConfig(&ctx->config);
|
||||||
ctx->config.enableTx = true;
|
ctx->config.enableTx = true;
|
||||||
|
|||||||
@@ -373,12 +373,15 @@ static int imxrt_lpi2c_hw_init(struct imxrt_lpi2c_bus *bus)
|
|||||||
return 0;
|
return 0;
|
||||||
}
|
}
|
||||||
|
|
||||||
static uint32_t imxrt_lpi2c_get_src_freq(void)
|
static uint32_t imxrt_lpi2c_get_src_freq(clock_ip_name_t clock_ip)
|
||||||
{
|
{
|
||||||
uint32_t freq;
|
uint32_t freq;
|
||||||
|
#if IMXRT_IS_MIMXRT10xx
|
||||||
uint32_t mux;
|
uint32_t mux;
|
||||||
uint32_t divider;
|
uint32_t divider;
|
||||||
|
|
||||||
|
(void) clock_ip; /* Not necessary for i.MXRT1050 */
|
||||||
|
|
||||||
mux = CLOCK_GetMux(kCLOCK_Lpi2cMux);
|
mux = CLOCK_GetMux(kCLOCK_Lpi2cMux);
|
||||||
divider = 1;
|
divider = 1;
|
||||||
|
|
||||||
@@ -396,6 +399,17 @@ static uint32_t imxrt_lpi2c_get_src_freq(void)
|
|||||||
|
|
||||||
divider *= CLOCK_GetDiv(kCLOCK_Lpi2cDiv) + 1;
|
divider *= CLOCK_GetDiv(kCLOCK_Lpi2cDiv) + 1;
|
||||||
freq /= divider;
|
freq /= divider;
|
||||||
|
#elif IMXRT_IS_MIMXRT11xx
|
||||||
|
/*
|
||||||
|
* FIXME: A future version of the mcux_sdk might provide a better method to
|
||||||
|
* get the clock instead of this hack.
|
||||||
|
*/
|
||||||
|
clock_root_t clock_root = clock_ip + kCLOCK_Root_Lpi2c1 - kCLOCK_Lpi2c1;
|
||||||
|
|
||||||
|
freq = CLOCK_GetRootClockFreq(clock_root);
|
||||||
|
#else
|
||||||
|
#error Getting I2C frequency is not implemented for this chip.
|
||||||
|
#endif
|
||||||
|
|
||||||
return freq;
|
return freq;
|
||||||
}
|
}
|
||||||
@@ -457,7 +471,7 @@ void imxrt_lpi2c_init(void)
|
|||||||
}
|
}
|
||||||
|
|
||||||
bus->clock_ip = imxrt_lpi2c_clock_ip(bus->regs);
|
bus->clock_ip = imxrt_lpi2c_clock_ip(bus->regs);
|
||||||
bus->src_clock_hz = imxrt_lpi2c_get_src_freq();
|
bus->src_clock_hz = imxrt_lpi2c_get_src_freq(bus->clock_ip);
|
||||||
|
|
||||||
eno = imxrt_lpi2c_hw_init(bus);
|
eno = imxrt_lpi2c_hw_init(bus);
|
||||||
if (eno != 0) {
|
if (eno != 0) {
|
||||||
|
|||||||
@@ -92,9 +92,17 @@ rtems_vector_number QTMR_get_IRQ_from_fdt(const void *fdt, int node)
|
|||||||
|
|
||||||
uint32_t QTMR_get_src_clk(TMR_Type *base)
|
uint32_t QTMR_get_src_clk(TMR_Type *base)
|
||||||
{
|
{
|
||||||
|
#if IMXRT_IS_MIMXRT10xx
|
||||||
(void) base;
|
(void) base;
|
||||||
|
|
||||||
return CLOCK_GetFreq(kCLOCK_IpgClk);
|
return CLOCK_GetFreq(kCLOCK_IpgClk);
|
||||||
|
#elif IMXRT_IS_MIMXRT11xx
|
||||||
|
(void) base;
|
||||||
|
|
||||||
|
return CLOCK_GetRootClockMux(kCLOCK_Root_Bus);
|
||||||
|
#else
|
||||||
|
#error Getting Timer clock frequency is not implemented for this chip
|
||||||
|
#endif
|
||||||
}
|
}
|
||||||
|
|
||||||
#endif /* __rtems__ */
|
#endif /* __rtems__ */
|
||||||
|
|||||||
@@ -477,12 +477,15 @@ static int imxrt_lpspi_setup(spi_bus *base)
|
|||||||
return rv;
|
return rv;
|
||||||
}
|
}
|
||||||
|
|
||||||
static uint32_t imxrt_lpspi_get_src_freq(void)
|
static uint32_t imxrt_lpspi_get_src_freq(clock_ip_name_t clock_ip)
|
||||||
{
|
{
|
||||||
uint32_t freq;
|
uint32_t freq;
|
||||||
|
#if IMXRT_IS_MIMXRT10xx
|
||||||
uint32_t mux;
|
uint32_t mux;
|
||||||
uint32_t divider;
|
uint32_t divider;
|
||||||
|
|
||||||
|
(void) clock_ip; /* Not necessary for i.MXRT1050 */
|
||||||
|
|
||||||
mux = CLOCK_GetMux(kCLOCK_LpspiMux);
|
mux = CLOCK_GetMux(kCLOCK_LpspiMux);
|
||||||
|
|
||||||
switch (mux) {
|
switch (mux) {
|
||||||
@@ -504,6 +507,17 @@ static uint32_t imxrt_lpspi_get_src_freq(void)
|
|||||||
|
|
||||||
divider = CLOCK_GetDiv(kCLOCK_LpspiDiv) + 1;
|
divider = CLOCK_GetDiv(kCLOCK_LpspiDiv) + 1;
|
||||||
freq /= divider;
|
freq /= divider;
|
||||||
|
#elif IMXRT_IS_MIMXRT11xx
|
||||||
|
/*
|
||||||
|
* FIXME: A future version of the mcux_sdk might provide a better method to
|
||||||
|
* get the clock instead of this hack.
|
||||||
|
*/
|
||||||
|
clock_root_t clock_root = clock_ip + kCLOCK_Root_Lpspi1 - kCLOCK_Lpspi1;
|
||||||
|
|
||||||
|
freq = CLOCK_GetRootClockFreq(clock_root);
|
||||||
|
#else
|
||||||
|
#error Getting SPI frequency is not implemented for this chip.
|
||||||
|
#endif
|
||||||
|
|
||||||
return freq;
|
return freq;
|
||||||
}
|
}
|
||||||
@@ -580,7 +594,7 @@ void imxrt_lpspi_init(void)
|
|||||||
}
|
}
|
||||||
|
|
||||||
bus->clock_ip = imxrt_lpspi_clock_ip(bus->regs);
|
bus->clock_ip = imxrt_lpspi_clock_ip(bus->regs);
|
||||||
bus->src_clock_hz = imxrt_lpspi_get_src_freq();
|
bus->src_clock_hz = imxrt_lpspi_get_src_freq(bus->clock_ip);
|
||||||
/* Absolut maximum is 30MHz according to electrical characteristics */
|
/* Absolut maximum is 30MHz according to electrical characteristics */
|
||||||
bus->base.max_speed_hz = MIN(bus->src_clock_hz / 2, 30000000);
|
bus->base.max_speed_hz = MIN(bus->src_clock_hz / 2, 30000000);
|
||||||
bus->base.delay_usecs = 0;
|
bus->base.delay_usecs = 0;
|
||||||
|
|||||||
Reference in New Issue
Block a user