feat(mpll): supported mpll configure ll api

This commit is contained in:
Armando 2023-12-19 17:20:21 +08:00
parent 4a2af43535
commit 27b1e4dc87
7 changed files with 142 additions and 1 deletions

View File

@ -7,6 +7,8 @@
#pragma once
#include <stdbool.h>
#include <stdint.h>
#include "soc/soc_caps.h"
#ifdef __cplusplus
extern "C" {
@ -44,6 +46,27 @@ void rtc_clk_bbpll_add_consumer(void);
*/
void rtc_clk_bbpll_remove_consumer(void);
#if SOC_CLK_MPLL_SUPPORTED
//------------------------------------MPLL-------------------------------------//
/**
* @brief Enable MPLL
*/
void rtc_clk_mpll_enable(void);
/**
* @brief Disable MPLL
*/
void rtc_clk_mpll_disable(void);
/**
* @brief Configure MPLL
*
* @param[in] xtal_freq XTAL frequency
* @param[in] mpll_freq MPLL frequency
*/
void rtc_clk_mpll_configure(uint32_t xtal_freq, uint32_t mpll_freq);
#endif //#if SOC_CLK_MPLL_SUPPORTED
#ifdef __cplusplus
}
#endif

View File

@ -405,3 +405,26 @@ bool rtc_dig_8m_enabled(void)
* TODO: update the library to use rtc_clk_xtal_freq_get
*/
rtc_xtal_freq_t rtc_get_xtal(void) __attribute__((alias("rtc_clk_xtal_freq_get")));
//------------------------------------MPLL-------------------------------------//
void rtc_clk_mpll_disable(void)
{
clk_ll_mpll_disable();
}
void rtc_clk_mpll_enable(void)
{
clk_ll_mpll_enable();
}
void rtc_clk_mpll_configure(uint32_t xtal_freq, uint32_t mpll_freq)
{
/* Analog part */
/* MPLL calibration start */
regi2c_ctrl_ll_mpll_calibration_start();
clk_ll_mpll_set_config(mpll_freq, xtal_freq);
/* wait calibration done */
while(!regi2c_ctrl_ll_mpll_calibration_is_done());
/* MPLL calibration stop */
regi2c_ctrl_ll_mpll_calibration_stop();
}

View File

@ -10,8 +10,9 @@
#include "soc/soc.h"
#include "soc/clk_tree_defs.h"
#include "soc/rtc.h"
#include "soc/pmu_reg.h"
#include "hal/regi2c_ctrl.h"
#include "soc/regi2c_bbpll.h"
#include "soc/regi2c_mpll.h"
#include "hal/assert.h"
#include "hal/log.h"
#include "esp32p4/rom/rtc.h"
@ -82,6 +83,22 @@ static inline __attribute__((always_inline)) void clk_ll_bbpll_disable(void)
}
/**
* @brief Power up MPLL circuit
*/
static inline __attribute__((always_inline)) void clk_ll_mpll_enable(void)
{
REG_SET_BIT(PMU_RF_PWC_REG, PMU_MSPI_PHY_XPD);
}
/**
* @brief Power down MPLL circuit
*/
static inline __attribute__((always_inline)) void clk_ll_mpll_disable(void)
{
REG_CLR_BIT(PMU_RF_PWC_REG, PMU_MSPI_PHY_XPD);
}
/**
* @brief Enable the 32kHz crystal oscillator
*
@ -272,6 +289,25 @@ static inline __attribute__((always_inline)) void clk_ll_bbpll_set_config(uint32
}
/**
* @brief Set MPLL frequency from XTAL source (Analog part - through regi2c)
*
* @param mpll_freq_mhz MPLL frequency, in MHz
* @param xtal_freq_mhz XTAL frequency, in MHz
*/
static inline __attribute__((always_inline)) void clk_ll_mpll_set_config(uint32_t mpll_freq_mhz, uint32_t xtal_freq_mhz)
{
HAL_ASSERT(xtal_freq_mhz == RTC_XTAL_FREQ_40M);
// MPLL_Freq = XTAL_Freq * (div + 1) / (ref_div + 1)
uint8_t ref_div = 1;
uint8_t div = mpll_freq_mhz / 20 - 1;
uint32_t val = REGI2C_READ(I2C_MPLL, I2C_MPLL_DIV_REG_ADDR);
val |= ((div << 3) | ref_div);
REGI2C_WRITE(I2C_MPLL, I2C_MPLL_DIV_REG_ADDR, val);
}
/**
* @brief Select the clock source for CPU_CLK (SOC Clock Root)
*

View File

@ -10,6 +10,7 @@
#include <stdint.h>
#include "soc/soc.h"
#include "soc/regi2c_defs.h"
#include "soc/hp_sys_clkrst_reg.h"
#ifdef __cplusplus
extern "C" {
@ -45,6 +46,32 @@ static inline __attribute__((always_inline)) bool regi2c_ctrl_ll_bbpll_calibrati
return REG_GET_BIT(I2C_MST_ANA_CONF0_REG, I2C_MST_BBPLL_CAL_DONE);
}
/**
* @brief Start MPLL self-calibration
*/
static inline __attribute__((always_inline)) void regi2c_ctrl_ll_mpll_calibration_start(void)
{
CLEAR_PERI_REG_MASK(HP_SYS_CLKRST_ANA_PLL_CTRL0_REG, HP_SYS_CLKRST_REG_MSPI_CAL_STOP);
}
/**
* @brief Stop MPLL self-calibration
*/
static inline __attribute__((always_inline)) void regi2c_ctrl_ll_mpll_calibration_stop(void)
{
SET_PERI_REG_MASK(HP_SYS_CLKRST_ANA_PLL_CTRL0_REG, HP_SYS_CLKRST_REG_MSPI_CAL_STOP);
}
/**
* @brief Check whether MPLL calibration is done
*
* @return True if calibration is done; otherwise false
*/
static inline __attribute__((always_inline)) bool regi2c_ctrl_ll_mpll_calibration_is_done(void)
{
return REG_GET_BIT(HP_SYS_CLKRST_ANA_PLL_CTRL0_REG, HP_SYS_CLKRST_REG_MSPI_CAL_END);
}
/**
* @brief Enable the I2C internal bus to do I2C read/write operation to the SAR_ADC register
*/

View File

@ -1307,6 +1307,10 @@ config SOC_CLK_APLL_SUPPORTED
bool
default y
config SOC_CLK_MPLL_SUPPORTED
bool
default y
config SOC_CLK_XTAL32K_SUPPORTED
bool
default y

View File

@ -0,0 +1,27 @@
/*
* SPDX-FileCopyrightText: 2023 Espressif Systems (Shanghai) CO LTD
*
* SPDX-License-Identifier: Apache-2.0
*/
#pragma once
/**
* @file regi2c_mpll.h
* @brief Register definitions for MSPI_PLL (MPLL)
*
* This file lists register fields of MPLL, located on an internal configuration
* bus. These definitions are used via macros defined in regi2c_ctrl.h
*/
#define I2C_MPLL 0x63
#define I2C_MPLL_HOSTID 0
#define I2C_MPLL_DIV_REG_ADDR 2
#define I2C_MPLL_REF_DIV_ADDR I2C_MPLL_DIV_REG_ADDR
#define I2C_MPLL_REF_DIV_ADDR_MSB 2
#define I2C_MPLL_REF_DIV_ADDR_LSB 0
#define I2C_MPLL_DIV_ADDR I2C_MPLL_DIV_REG_ADDR
#define I2C_MPLL_DIV_ADDR_MSB 7
#define I2C_MPLL_DIV_ADDR_LSB 3

View File

@ -563,6 +563,7 @@
#define SOC_MODEM_CLOCK_IS_INDEPENDENT (0)
#define SOC_CLK_APLL_SUPPORTED (1) /*!< Support Audio PLL */
#define SOC_CLK_MPLL_SUPPORTED (1) /*!< Support MSPI PLL */
#define SOC_CLK_XTAL32K_SUPPORTED (1) /*!< Support to connect an external low frequency crystal */
#define SOC_CLK_OSC_SLOW_SUPPORTED (1) /*!< Support to connect an external oscillator, not a crystal */
#define SOC_CLK_RC32K_SUPPORTED (1) /*!< Support an internal 32kHz RC oscillator */