#include "uptime.h" 

#define ONE_DAY_RESET_SEC       86400

#define TASK_LIST_SIZE          6

static uint32_t uptime = 0;

task_list_t task_list[TASK_LIST_SIZE];
static uint8_t task_number = 0;

//
void get_uptime(uint32_t *value)
{
    *value = uptime;
}


//
void uptime_init(void)
{
    crm_clocks_freq_type crm_clocks_freq_struct = {0};
    
    crm_periph_clock_enable(CRM_TMR6_PERIPH_CLOCK, TRUE);

    crm_clocks_freq_get(&crm_clocks_freq_struct);
    tmr_base_init(TMR6, 9999, (crm_clocks_freq_struct.ahb_freq / 20000) - 1);
    tmr_cnt_dir_set(TMR6, TMR_COUNT_UP);
        
    tmr_flag_clear(TMR6, TMR_OVF_FLAG);

    nvic_priority_group_config(NVIC_PRIORITY_GROUP_4);
    nvic_irq_enable(TMR6_GLOBAL_IRQn, 5, 0);
       
    tmr_counter_enable(TMR6, TRUE);
    
    tmr_interrupt_enable(TMR6, TMR_OVF_INT, TRUE);
}


//
#if 0
void TMR6_GLOBAL_IRQHandler(void)
{
    if(tmr_flag_get(TMR6, TMR_OVF_FLAG) != RESET)
    {
        tmr_flag_clear(TMR6, TMR_OVF_FLAG);
        uptime++;
        
        if (uptime >= ONE_DAY_RESET_SEC) {
            nvic_system_reset();
        }
        
        wdt_task_process();
    }
}
#endif

//
uint8_t wdt_add_task(uint32_t max)
{
    if (task_number == TASK_LIST_SIZE)
        return 0;
    task_list[task_number++].max_cnt = max;
    return task_number - 1;
}


//
void wdt_reset_cnt(uint8_t id)
{
    task_list[id].cnt = 0;
}


//
void wdt_task_process(void) 
{
    for (uint8_t i = 0; i < task_number; i++)
    {
        if (task_list[i].cnt++ > task_list[i].max_cnt) 
        {
            //printf("Alarm! Task id %u wdt error!\r\n", i);
            NVIC_SystemReset();
        }
    }
}