rt-thread/bsp/hc32f4a0/Libraries/HC32F4A0_StdPeriph_Driver/src/hc32f4a0_fmac.c

351 lines
13 KiB
C

/**
*******************************************************************************
* @file hc32f4a0_fmac.c
* @brief This file provides firmware functions to manage the Filter Math
* Accelerate (FMAC).
@verbatim
Change Logs:
Date Author Notes
2020-06-12 Heqb First version
@endverbatim
*******************************************************************************
* Copyright (C) 2020, Huada Semiconductor Co., Ltd. All rights reserved.
*
* This software component is licensed by HDSC under BSD 3-Clause license
* (the "License"); You may not use this file except in compliance with the
* License. You may obtain a copy of the License at:
* opensource.org/licenses/BSD-3-Clause
*
*******************************************************************************
*/
/*******************************************************************************
* Include files
******************************************************************************/
#include "hc32f4a0_fmac.h"
#include "hc32f4a0_utility.h"
/**
* @addtogroup HC32F4A0_DDL_Driver
* @{
*/
/**
* @defgroup DDL_FMAC FMAC
* @brief FMAC Driver Library
* @{
*/
#if (DDL_FMAC_ENABLE == DDL_ON)
/*******************************************************************************
* Local type definitions ('typedef')
******************************************************************************/
/*******************************************************************************
* Local pre-processor symbols/macros ('#define')
******************************************************************************/
/**
* @defgroup FMAC_Local_Macros FMAC Local Macros
* @{
*/
/**
* @defgroup FMAC_Check_Parameters_Validity FMAC Check Parameters Validity
* @{
*/
#define IS_FMAC_FILTER_SHIFT(x) ((x) <= FMAC_FILTER_SHIFT_21BIT)
#define IS_FMAC_FILTER_STAGE(x) ((x) <= FMAC_FILTER_STAGE_16)
#define IS_FMAC_INT_FUNC(x) \
( ((x) == FMAC_INT_ENABLE) || \
((x) == FMAC_INT_DISABLE))
#define IS_VALID_UNIT(x) \
( ((x) == M4_FMAC1) || \
((x) == M4_FMAC2) || \
((x) == M4_FMAC3) || \
((x) == M4_FMAC4))
/**
* @}
*/
/**
* @}
*/
/*******************************************************************************
* Global variable definitions (declared in header file with 'extern')
******************************************************************************/
/*******************************************************************************
* Local function prototypes ('static')
******************************************************************************/
/*******************************************************************************
* Local variable definitions ('static')
******************************************************************************/
/*******************************************************************************
* Function implementation - global ('extern') and local ('static')
******************************************************************************/
/**
* @defgroup FMAC_Global_Functions FMAC Global Functions
* @{
*/
/**
* @brief FMAC peripheral initialization stucture clear
* @param [in] pstcInitStruct FMAC function structure
* @arg See the structure definition for @ref stc_fmac_init_t
* @retval Ok: Success
* ErrorInvalidParameter: Parameter error
*/
en_result_t FMAC_StructInit(stc_fmac_init_t* pstcInitStruct)
{
en_result_t enRet = ErrorInvalidParameter;
if (pstcInitStruct != NULL)
{
pstcInitStruct->u32FiltStage = FMAC_FILTER_STAGE_0;
pstcInitStruct->u32FiltShift = FMAC_FILTER_SHIFT_0BIT;
pstcInitStruct->i16FiltFactor = 0;
pstcInitStruct->u32IntCmd = FMAC_INT_DISABLE;
enRet = Ok;
}
return enRet;
}
/**
* @brief De-Initialize FMAC function
* @param [in] FMACx Pointer to FMAC instance register base.
* This parameter can be a value of the following:
* @arg M4_FMAC1: FMAC unit 1 instance register base
* @arg M4_FMAC2: FMAC unit 2 instance register base
* @arg M4_FMAC3: FMAC unit 3 instance register base
* @arg M4_FMAC4: FMAC unit 4 instance register base
* @retval None
*/
void FMAC_DeInit(M4_FMAC_TypeDef* FMACx)
{
DDL_ASSERT(IS_VALID_UNIT(FMACx));
WRITE_REG32(FMACx->CTR, 0UL);
WRITE_REG32(FMACx->IER, 0UL);
WRITE_REG32(FMACx->DTR, 0UL);
WRITE_REG32(FMACx->RTR0, 0UL);
WRITE_REG32(FMACx->RTR1, 0UL);
WRITE_REG32(FMACx->STR, 0UL);
}
/**
* @brief FMAC peripheral function initialize
* @param [in] FMACx Pointer to FMAC instance register base.
* This parameter can be a value of the following:
* @arg M4_FMAC1: FMAC unit 1 instance register base
* @arg M4_FMAC2: FMAC unit 2 instance register base
* @arg M4_FMAC3: FMAC unit 3 instance register base
* @arg M4_FMAC4: FMAC unit 4 instance register base
* @param [in] pstcFmacInit FMAC function base parameter structure
* @arg See the structure definition for @ref stc_fmac_init_t
* @retval Ok: Success
* ErrorInvalidParameter: Parameter error
*/
en_result_t FMAC_Init(M4_FMAC_TypeDef* FMACx, const stc_fmac_init_t *pstcFmacInit)
{
en_result_t enRet = ErrorInvalidParameter;
__IO uint32_t *FMAC_CORx;
uint32_t u32temp;
if(pstcFmacInit != NULL)
{
DDL_ASSERT(IS_VALID_UNIT(FMACx));
DDL_ASSERT(IS_FMAC_FILTER_SHIFT(pstcFmacInit->u32FiltShift));
DDL_ASSERT(IS_FMAC_FILTER_STAGE(pstcFmacInit->u32FiltStage));
DDL_ASSERT(IS_FMAC_INT_FUNC(pstcFmacInit->u32IntCmd));
u32temp = pstcFmacInit->u32FiltStage;
/* Configure filter stage and results right shift bits */
WRITE_REG32(FMACx->CTR, (pstcFmacInit->u32FiltStage | \
(pstcFmacInit->u32FiltShift << FMAC_CTR_SHIFT_POS)));
/* Configure interrupt command */
WRITE_REG32(FMACx->IER, pstcFmacInit->u32IntCmd);
do{
FMAC_CORx = (__IO uint32_t *)((uint32_t)(&FMACx->COR0) + (u32temp << 2UL));
WRITE_REG32(*FMAC_CORx, pstcFmacInit->i16FiltFactor);
}while((u32temp--) > 0UL);
enRet = Ok;
}
return enRet;
}
/**
* @brief Enable or Disable FMAC
* @param [in] FMACx Pointer to FMAC instance register base.
* This parameter can be a value of the following:
* @arg M4_FMAC1: FMAC unit 1 instance register base
* @arg M4_FMAC2: FMAC unit 2 instance register base
* @arg M4_FMAC3: FMAC unit 3 instance register base
* @arg M4_FMAC4: FMAC unit 4 instance register base
* @param [in] enNewState Disable or Enable the function
* @retval None
*/
void FMAC_Cmd(M4_FMAC_TypeDef* FMACx, en_functional_state_t enNewState)
{
DDL_ASSERT(IS_VALID_UNIT(FMACx));
DDL_ASSERT(IS_FUNCTIONAL_STATE(enNewState));
WRITE_REG32(FMACx->ENR, enNewState);
}
/**
* @brief Set Filter result shift bits.
* @param [in] FMACx Pointer to FMAC instance register base.
* This parameter can be a value of the following:
* @arg M4_FMAC1: FMAC unit 1 instance register base
* @arg M4_FMAC2: FMAC unit 2 instance register base
* @arg M4_FMAC3: FMAC unit 3 instance register base
* @arg M4_FMAC4: FMAC unit 4 instance register base
* @param [in] u32ShiftNum Result shift times.
* This parameter can be set 0-21
* @retval None
*/
void FMAC_SetResultShift(M4_FMAC_TypeDef* FMACx, uint32_t u32ShiftNum)
{
DDL_ASSERT(IS_VALID_UNIT(FMACx));
DDL_ASSERT(IS_FMAC_FILTER_SHIFT(u32ShiftNum));
/* Set Filter result shift bits */
MODIFY_REG32(FMACx->CTR, FMAC_CTR_SHIFT, u32ShiftNum << FMAC_CTR_SHIFT_POS);
}
/**
* @brief Set filter stage and filter factor.
* @param [in] FMACx Pointer to FMAC instance register base.
* This parameter can be a value of the following:
* @arg M4_FMAC1: FMAC unit 1 instance register base
* @arg M4_FMAC2: FMAC unit 2 instance register base
* @arg M4_FMAC3: FMAC unit 3 instance register base
* @arg M4_FMAC4: FMAC unit 4 instance register base
* @param [in] u32FilterStage FMAC filter stage.
* This parameter can be set 0 ~ 16
* @param [in] i16Factor FMAC filter factor.
* This parameter can be set -32768 ~ 32767
* @retval None
*/
void FMAC_SetStageFactor(M4_FMAC_TypeDef* FMACx, uint32_t u32FilterStage, int16_t i16Factor)
{
__IO uint32_t *FMAC_CORx;
DDL_ASSERT(IS_VALID_UNIT(FMACx));
DDL_ASSERT(IS_FMAC_FILTER_STAGE(u32FilterStage));
/* FMAC Software reset */
CLEAR_REG32_BIT(FMACx->ENR, FMAC_ENR_FMACEN);
SET_REG32_BIT(FMACx->ENR, FMAC_ENR_FMACEN);
/* Set the filter stage */
MODIFY_REG32(FMACx->CTR, FMAC_CTR_STAGE_NUM, u32FilterStage);
do
{
FMAC_CORx = (__IO uint32_t*)((uint32_t)(&FMACx->COR0) + (u32FilterStage << 2UL));
WRITE_REG32(*FMAC_CORx, i16Factor);
}while((u32FilterStage--) > 0UL);
}
/**
* @brief Configure interrupt command.
* @param [in] FMACx Pointer to FMAC instance register base.
* This parameter can be a value of the following:
* @arg M4_FMAC1: FMAC unit 1 instance register base
* @arg M4_FMAC2: FMAC unit 2 instance register base
* @arg M4_FMAC3: FMAC unit 3 instance register base
* @arg M4_FMAC4: FMAC unit 4 instance register base
* @param [in] enNewState Disable or Enable the function.
* @retval None
*/
void FMAC_IntCmd(M4_FMAC_TypeDef* FMACx, en_functional_state_t enNewState)
{
DDL_ASSERT(IS_VALID_UNIT(FMACx));
DDL_ASSERT(IS_FUNCTIONAL_STATE(enNewState));
WRITE_REG32(FMACx->IER, enNewState);
}
/**
* @brief Data input.
* @param [in] FMACx Pointer to FMAC instance register base.
* This parameter can be a value of the following:
* @arg M4_FMAC1: FMAC unit 1 instance register base
* @arg M4_FMAC2: FMAC unit 2 instance register base
* @arg M4_FMAC3: FMAC unit 3 instance register base
* @arg M4_FMAC4: FMAC unit 4 instance register base
* @param [in] i16Factor Data that needs to be processed.
* @retval None
*/
void FMAC_FIRInput(M4_FMAC_TypeDef* FMACx, int16_t i16Factor)
{
DDL_ASSERT(IS_VALID_UNIT(FMACx));
WRITE_REG32(FMACx->DTR, i16Factor);
}
/**
* @brief Get FMAC status.
* @param [in] FMACx Pointer to FMAC instance register base.
* This parameter can be a value of the following:
* @arg M4_FMAC1: FMAC unit 1 instance register base
* @arg M4_FMAC2: FMAC unit 2 instance register base
* @arg M4_FMAC3: FMAC unit 3 instance register base
* @arg M4_FMAC4: FMAC unit 4 instance register base
* @retval Set Calculate complete
* Reset Calculation in progress
*/
en_flag_status_t FMAC_GetStatus(const M4_FMAC_TypeDef* FMACx)
{
DDL_ASSERT(IS_VALID_UNIT(FMACx));
return (READ_REG32_BIT(FMACx->STR, FMAC_STR_READY) ? Set : Reset);
}
/**
* @brief Get calculation results.
* @param [in] FMACx Pointer to FMAC instance register base.
* This parameter can be a value of the following:
* @arg M4_FMAC1: FMAC unit 1 instance register base
* @arg M4_FMAC2: FMAC unit 2 instance register base
* @arg M4_FMAC3: FMAC unit 3 instance register base
* @arg M4_FMAC4: FMAC unit 4 instance register base
* @param [out] stcResult Get result.
* u32ResultHigh: The high value of the result
* u32ResultLow: The low value of the result
* @retval Ok: Success
* ErrorInvalidParameter: stcResult == NULL
*/
en_result_t FMAC_GetResult(const M4_FMAC_TypeDef* FMACx, stc_fmac_result_t *stcResult)
{
en_result_t enRet = ErrorInvalidParameter;
DDL_ASSERT(IS_VALID_UNIT(FMACx));
if (stcResult != NULL)
{
stcResult->u32ResultHigh = READ_REG32(FMACx->RTR0);
stcResult->u32ResultLow = READ_REG32(FMACx->RTR1);
enRet = Ok;
}
return enRet;
}
/**
* @}
*/
#endif /* DDL_FMAC_ENABLE */
/**
* @}
*/
/**
* @}
*/
/*******************************************************************************
* EOF (not truncated)
******************************************************************************/