/*!
 * @file        bmp561_tmr.c
 *
 * @brief       This file provides all the TMR firmware functions
 *
 * @version     V1.0.0
 *
 * @date        2025-01-01
 *
 * @attention
 *
 *  Copyright (C) 2025 Geehy Semiconductor
 *
 *  You may not use this file except in compliance with the
 *  GEEHY COPYRIGHT NOTICE (GEEHY SOFTWARE PACKAGE LICENSE).
 *
 *  The program is only for reference, which is distributed in the hope
 *  that it will be useful and instructional for customers to develop
 *  their software. Unless required by applicable law or agreed to in
 *  writing, the program is distributed on an "AS IS" BASIS, WITHOUT
 *  ANY WARRANTY OR CONDITIONS OF ANY KIND, either express or implied.
 *  See the GEEHY SOFTWARE PACKAGE LICENSE for the governing permissions
 *  and limitations under the License.
 */

#include "bmp561_tmr.h"
#include "bmp561_sysctrl.h"

/** @addtogroup Peripherals_Library Standard Peripheral Library
  @{
*/

/** @addtogroup TMR_Driver  TMR Driver
  @{
*/

/** @addtogroup TMR_Functions Functions
  @{
*/


/*!
 * @brief     Resets the TMR peripheral registers to their default reset values.
 *
 * @param     tmr: The TMRx can be 0 or 1.
 *
 * @retval    None
 *
 */
void TMR_Reset(TMR_T* tmr)
{
    SYSCTRL_Unlock();
    if(tmr == TMR0)
    {
        SYSCTRL_EnableAPBPeriphReset(SYSCTRL_APB_TMR0);
        SYSCTRL_DisableAPBPeriphReset(SYSCTRL_APB_TMR0);
    }
    else
    {
        SYSCTRL_EnableAPBPeriphReset(SYSCTRL_APB_TMR1);
        SYSCTRL_DisableAPBPeriphReset(SYSCTRL_APB_TMR1);
    }
    SYSCTRL_Lock();
}

/*!
 * @brief     Enables the specified TMR peripheral.
 *
 * @param     tmr: The TMRx can be 0 or 1.
 *
 * @retval    None
 *
 */
void TMR_Enable(TMR_T* tmr)
{
    tmr->CTRL_B.EN = BIT_SET;
}

/*!
 * @brief     Disables the specified TMR peripheral.
 *
 * @param     tmr: The TMRx can be 0 or 1.
 *
 * @retval    None
 *
 */
void TMR_Disable(TMR_T* tmr)
{
    tmr->CTRL_B.EN = BIT_RESET;
}

/*!
 * @brief     Configures the specified TMR mode.
 *
 * @param     tmr: The TMRx can be 0 or 1.
 *
 * @param     TIM_Mode: specifies the work Mode.
 *                      The parameter can be one of the following values:
 *                      @arg TMR_MODE_TMR: TIMER mode
 *                      @arg TMR_MODE_PWM: PWM mode
 * @retval    None
 *
 */
void TMR_ConfigMode(TMR_T* tmr, TMR_MODE_T mode)
{
    tmr->CTRL_B.MODE = mode;
}

/*!
 * @brief     Enables the specified TMR reload to buff when counter occurs overflow.
 *
 * @param     tmr: The TMRx can be 0 or 1.
 *
 * @retval    None
 *
 */
void TMR_EnableOverflowReload(TMR_T* tmr)
{
    tmr->CTRL_B.BUFEN = BIT_SET;
}

/*!
 * @brief     Disables the specified TMR reload to buff when counter occurs overflow.
 *
 * @param     tmr: The TMRx can be 0 or 1.
 *
 * @retval    None
 *
 */
void TMR_DisableOverflowReload(TMR_T* tmr)
{
    tmr->CTRL_B.BUFEN = BIT_RESET;
}

/*!
 * @brief     Configures the specified TMR clock divisor.
 *
 * @param     tmr: The TMRx can be 0 or 1.
 *
 * @param     div: specifies the clock divisor.
 *                 The parameter can be one of the following value:
 *                 @arg TMR_DIV_1    : TMR clock = Fsys/2^0
 *                 @arg TMR_DIV_2    : TMR clock = Fsys/2^1
 *                 @arg TMR_DIV_4    : TMR clock = Fsys/2^2
 *                 @arg TMR_DIV_8    : TMR clock = Fsys/2^3
 *                 @arg TMR_DIV_16   : TMR clock = Fsys/2^4
 *                 @arg TMR_DIV_32   : TMR clock = Fsys/2^5
 *                 @arg TMR_DIV_64   : TMR clock = Fsys/2^6
 *                 @arg TMR_DIV_128  : TMR clock = Fsys/2^7
 *                 @arg TMR_DIV_256  : TMR clock = Fsys/2^8
 *                 @arg TMR_DIV_512  : TMR clock = Fsys/2^9
 *                 @arg TMR_DIV_1024 : TMR clock = Fsys/2^10
 *                 @arg TMR_DIV_OTHER: TMR clock = Fsys/2^10
 *
 * @retval    None
 *
 */
void TMR_ConfigClockDiv(TMR_T* tmr, TMR_DIV_T div)
{
    tmr->CTRL_B.PS = div;
}

/*!
 * @brief     Configures the specified TMR PWM mode duty ratio polarity.
 *
 * @param     tmr: The TMRx can be 0 or 1.
 *
 * @param     levelType: specifies the TMRx work as PWM mode duty ratio output level type.
 *                       The parameter can be one of the following values:
 *                       @arg TMR_PWM_POL_HIGH: TIMER mode
 *                       @arg TMR_PWM_POL_LOW : PWM mode
 * @retval    None
 *
 */
void TMR_PWM_ConfigPolarity(TMR_T* tmr, TMR_PWM_POL_T levelType)
{
    tmr->CTRL_B.PWMXS = levelType;
}

/*!
 * @brief     Configures the specified TMR PWM mode duty ratio.
 *
 * @param     tmr: The TMRx can be 0 or 1.
 *
 * @param     ratio: specifies the TMRx work as PWM mode duty ratio counter value.
 *                   The parameter can be configured from 0 to 0xFFFF.
 *
 * @retval    None
 *
 * @note      This register only can be used in PWM mode.
 *
 */
void TMR_PWM_ConfigDutyRatio(TMR_T* tmr, uint16_t ratio)
{
    tmr->PWMXD = (uint32_t)ratio;
}

/*!
 * @brief     Sets the specified TMR counter.
 *
 * @param     tmr: The TMRx can be 0 or 1.
 *
 * @param     counter: specifies the counter register new value.
 *                     The parameter can be configured from 0 to 0xFFFF.
 *
 * @retval    None
 *
 */
void TMR_SetCounter(TMR_T* tmr, uint16_t counter)
{
    tmr->ARV = (uint32_t)counter;
}

/*!
 * @brief     Gets the specified TMR counter.
 *
 * @param     tmr: The TMRx can be 0 or 1.
 *
 * @retval    Timer mode : Counter is max count value.
 *            PWM mode   : Counter is PWM period.
 *
 */
uint16_t TMR_GetCounter(TMR_T* tmr)
{
    return (uint16_t)tmr->CNT;
}

/*!
 * @brief     Enables the TMR interrupt.
 *
 * @param     tmr: The TMRx can be 0 or 1.
 *
 * @param     interrupt: specifies the interrupt.
 *                       The parameter can be one of following values:
 *                       @arg TMR_INT_OV : overflow interrupt
 *                       @arg TMR_INT_PWM: PWM mode counter arrived register PWMXD's value occurs interrupt
 *
 * @retval    None
 */
void TMR_EnableInterrupt(TMR_T* tmr, TMR_INT_T interrupt)
{
    tmr->IEN |= interrupt;
}

/*!
 * @brief     Disables the TMR interrupt.
 *
 * @param     tmr: The TMRx can be 0 or 1.
 *
 * @param     interrupt: specifies the interrupt.
 *                       The parameter can be one of the following values:
 *                       @arg TMR_INT_OV : overflow interrupt
 *                       @arg TMR_INT_PWM: PWM mode counter arrived register PWMXD's value occurs interrupt
 *
 * @retval    None
 */
void TMR_DisableInterrupt(TMR_T* tmr, TMR_INT_T interrupt)
{
    tmr->IEN &= ~interrupt;
}

/*!
 * @brief     Check whether the ITflag is set or reset
 *
 * @param     tmr: The TMRx can be 0 to 1
 *
 * @param     flag: specifies the TMR interrupts flag.
 *                  The parameter can be one of the following values:
 *                       @arg TMR_INT_OV : overflow interrupt
 *                       @arg TMR_INT_PWM: PWM mode counter arrived register PWMXD's value occurs interrupt
 *
 * @retval    The interrupt flag.
 *
 */
uint16_t TMR_ReadIntFlag(TMR_T* tmr, TMR_INT_T flag)
{
    return (tmr->SR & flag) ? BIT_SET : BIT_RESET;
}

/*!
 * @brief     Clears the TMR interrupt pending bits.
 *
 * @param     tmr: The TMRx can be 0 to 1
 *
 * @param     flag: specifies the TMR interrupts flag.
 *                  The parameter can be one of the following values:
 *                       @arg TMR_INT_OV : overflow interrupt
 *                       @arg TMR_INT_PWM: PWM mode counter arrived register PWMXD's value occurs interrupt
 *
 * @retval    None
 *
 */
void TMR_ClearIntFlag(TMR_T* tmr, TMR_INT_T flag)
{
    tmr->SCR |= flag;
}

/**@} end of group TMR_Functions*/
/**@} end of group TMR_Driver*/
/**@} end of group Peripherals_Library*/
