106 lines
2.7 KiB
C
106 lines
2.7 KiB
C
/**
|
|
* @file sdrv_fs24m_hw_access.c
|
|
* @brief taishan fs24m hw access source file.
|
|
*
|
|
* @copyright Copyright (c) 2022 Semidrive Semiconductor.
|
|
* All rights reserved.
|
|
*/
|
|
|
|
#include <bits.h>
|
|
|
|
#include "sdrv_fs24m_hw_access.h"
|
|
#include "sdrv_ckgen_common.h"
|
|
|
|
#define FS24M_WAIT_TIME 500000u
|
|
|
|
void sdrv_fs24m_xtal_sel(uint32_t base, uint8_t src)
|
|
{
|
|
RMWREG32(base + FS24M_GLB_CTL, FS24M_GLB_CTL_XTAL_SRC_SEL, 1u, src);
|
|
}
|
|
|
|
void sdrv_fs24m_fs_sel(uint32_t base, uint8_t src)
|
|
{
|
|
RMWREG32(base + FS24M_GLB_CTL, FS24M_GLB_CTL_FS_SRC_SEL, 1u, src);
|
|
}
|
|
|
|
uint32_t sdrv_fs24m_fs_sel_get(uint32_t base)
|
|
{
|
|
if (BIT(readl(base + FS24M_GLB_CTL), FS24M_GLB_CTL_XTAL_ACTIVE)) {
|
|
return FS24M_FS_SEL_XTAL;
|
|
}
|
|
else {
|
|
return FS24M_FS_SEL_RC;
|
|
}
|
|
}
|
|
|
|
int sdrv_fs24m_wait_active(uint32_t base, uint8_t src, uint32_t count)
|
|
{
|
|
uint32_t reg = base + FS24M_GLB_CTL;
|
|
uint32_t offset;
|
|
|
|
if (src == FS24M_FS_SEL_RC) {
|
|
offset = FS24M_GLB_CTL_RC_ACTIVE;
|
|
}
|
|
else {
|
|
offset = FS24M_GLB_CTL_XTAL_ACTIVE;
|
|
}
|
|
|
|
return sdrv_ckgen_wait(reg, offset, 1u, count);
|
|
}
|
|
|
|
int sdrv_fs24m_wait_ready(uint32_t base, uint8_t src, uint32_t count)
|
|
{
|
|
uint32_t reg = base + FS24M_GLB_CTL;
|
|
uint32_t offset;
|
|
|
|
if (src == FS24M_FS_SEL_RC) {
|
|
offset = FS24M_GLB_CTL_RC_RDY;
|
|
}
|
|
else {
|
|
offset = FS24M_GLB_CTL_XTAL_RDY;
|
|
}
|
|
|
|
/* timeout value 1 second */
|
|
return sdrv_ckgen_wait_timeout(reg, offset, 1u, 1000000u);
|
|
}
|
|
|
|
void sdrv_fs24m_xtal_fs_enable(uint32_t base, bool enable)
|
|
{
|
|
RMWREG32(base + FS24M_GLB_CTL, FS24M_GLB_CTL_FS_XTAL_EN, 1u, enable);
|
|
}
|
|
|
|
void sdrv_fs24m_rc_fs_enable(uint32_t base, bool enable)
|
|
{
|
|
RMWREG32(base + FS24M_GLB_CTL, FS24M_GLB_CTL_FS_OSC_EN, 1u, enable);
|
|
}
|
|
|
|
void sdrv_fs24m_xtal_enable(uint32_t base, bool enable)
|
|
{
|
|
RMWREG32(base + FS24M_XTAL_CTRL, FS24M_XTAL_CTRL_XTAL_ENABLE, 1u, enable);
|
|
}
|
|
|
|
void sdrv_fs24m_xtal_test_enable(uint32_t base, bool enable)
|
|
{
|
|
RMWREG32(base + FS24M_XTAL_CTRL, FS24M_XTAL_CTRL_XTAL_TEST_ENABLE, 1u, enable);
|
|
}
|
|
|
|
uint32_t sdrv_fs24m_get_32k_frequency_counter(uint32_t base)
|
|
{
|
|
uint32_t addr = base + FS24M_RC32K_CHK_CTL;
|
|
bool ret;
|
|
|
|
RMWREG32(addr, FS24M_RC32K_CHK_CTL_MON_EN_LSB, 1, 0);
|
|
sdrv_ckgen_wait(addr, FS24M_RC32K_CHK_CTL_MON_EN_STA_LSB, 0, FS24M_WAIT_TIME);
|
|
|
|
RMWREG32(addr, FS24M_RC32K_CHK_CTL_MON_EN_LSB, 1, 1);
|
|
|
|
ret = sdrv_ckgen_wait(addr, FS24M_RC32K_CHK_CTL_MON_EN_STA_LSB, 1, FS24M_WAIT_TIME);
|
|
if (ret) {
|
|
return ((readl(addr) >> FS24M_RC32K_CHK_CTL_FREQ_CNT_STA_LSB)
|
|
& FS24M_RC32K_CHK_CTL_FREQ_CNT_STA_MASK);
|
|
}
|
|
else {
|
|
return 0;
|
|
}
|
|
}
|