Newer
Older
BIRMM-GT200N / rtc.c

#include <stdio.h>
#include <stdlib.h>
#include <string.h>
#include "gsdk_sdk.h"
#include "gsdk_ril.h"
#include "rtc.h"
#include "AiderProtocol.h"

#define DEBUG_LOG(fmt,...) printf("[LOGD]:F:%s,L:%d,"fmt,__func__,__LINE__,##__VA_ARGS__);
#define WARN_LOG(fmt,...) printf("[LOGW]:"fmt,##__VA_ARGS__);

extern struct DeviceSet DeviceConfig;

static gsdk_handle_t rtc_handle;

void rtc_alarm_cb(void *user_data)
{
	(void)user_data;
	gsdk_ril_init();
	gsdk_ril_set_hardware_reboot();//重启模块
	OEM_LOGI("[RTC_DEMO] rtc alarm handle cb------------------------0!\n");
}

void utc_to_bj_time(rtc_time_t rtc_time)
{
	int year,month,day,hour;
	int lastday = 0;					//last day of this month
	int lastlastday = 0;			//last day of last month
	char temp_buf[100]  = {0};

	year	 = rtc_time.rtc_year + 2000;	//utc time
	month  	 = rtc_time.rtc_mon;
	day 	 = rtc_time.rtc_day;
	hour 	 = rtc_time.rtc_hour + 8;

	if(month==1 || month==3 || month==5 || month==7 || month==8 || month==10 || month==12)
	{
		lastday = 31;
		lastlastday = 30;//这里应该添加上个月的天数

		if(month == 3)
		{
			if((year%400 == 0)||(year%4 == 0 && year%100 != 0))//if this is lunar year
				lastlastday = 29;
			else
				lastlastday = 28;
		}

		if(month == 8 || month == 1)//这里应该是8月和1月,因为8月和1月的上一个月的天数是31天的
			lastlastday = 31;
	}
	else if(month == 4 || month == 6 || month == 9 || month == 11)
	{
		lastday = 30;
		lastlastday = 31;
	}
	else
	{
		lastlastday = 31;

		if((year%400 == 0)||(year%4 == 0 && year%100 != 0))
			lastday = 29;
		else
			lastday = 28;
	}

	if(hour >= 24) 					// if >24, day+1
	{
		hour -= 24;
		day += 1;

		if(day > lastday)  		// next month,  day-lastday of this month
		{
			day -= lastday;
			month += 1;

			if(month > 12) 		//	next year , month-12
			{
				month -= 12;
				year += 1;
			}
		}
	}
	if(hour < 0) 										// if <0, day-1
	{
		hour += 24;
		day -= 1;
		if(day < 1) 					  // month-1, day=last day of last month
		{
			day = lastlastday;
			month -= 1;
			if(month < 1)  			// last year , month=12
			{
				month = 12;
				year -= 1;
			}
		}
	}

	sprintf(temp_buf,
	        "Beijing time,%4d,%02d,%02d,%02d,%02d,%02d",
	        year,
	        month,
	        day,
	        hour,
	        rtc_time.rtc_min,
	        rtc_time.rtc_sec);

	OEM_LOGI("当前时间:  %s!\n", temp_buf);

	DeviceConfig.Time_Year = year-2000;/* 系统日期,OID:0x10000050 */
	DeviceConfig.Time_Mon = month;
	DeviceConfig.Time_Mday = day;
	DeviceConfig.Time_Hour = hour;
	DeviceConfig.Time_Min = rtc_time.rtc_min;
}

/*******************************************************************************
* Function Name  : RTC_Init
* Description    : RTC初始化,读取系统时间
* Input          : struct DeviceSet* DeviceConfig
* Output         : none
* Return         : 1成功,-1失败
*******************************************************************************/
int RTC_Init(void)
{
	rtc_time_t rtc_time = {0};
	gsdk_status_t status;

	status = gsdk_rtc_open(&rtc_handle);
	if (status != GSDK_SUCCESS)
	{
		OEM_LOGE("[RTC_DEMO] gsdk_rtc_open failed!\n");
		goto _fail;
	}

	status = gsdk_rtc_time_read(rtc_handle, &rtc_time);
	if (status != GSDK_SUCCESS)
	{
		OEM_LOGE("[RTC_DEMO] gsdk_rtc_time_read failed!\n");
		goto _fail;
	}

	utc_to_bj_time(rtc_time);

	return 1;

_fail:
	OEM_LOGI("[RTC_DEMO] RTC_Init failed!\n");
	gsdk_rtc_close(rtc_handle);
	return -1;
}

/*******************************************************************************
* Function Name  : RTC_Timing
* Description    : RTC校时
* Input          : uint8_t SetTime_Flag(1时间恢复出厂设置,2时间设置为服务器校时时间), struct DeviceSet DeviceConfig
* Output         : none
* Return         : 1成功,-1失败
*******************************************************************************/
int RTC_Timing(uint8_t SetTime_Flag)
{
	rtc_time_t rtc_time = {0};
	gsdk_status_t status;

	if(SetTime_Flag == 1)
	{
		OEM_LOGI("UE will adjust rtc time\r\n");
		rtc_time.rtc_year = 21;
		rtc_time.rtc_mon  = 1;
		rtc_time.rtc_day  = 1;
		rtc_time.rtc_week = 1;
		rtc_time.rtc_hour = 1;
		rtc_time.rtc_min  = 1;
		rtc_time.rtc_sec  = 1;

		status = gsdk_rtc_time_write(rtc_handle, &rtc_time);
		if (status != GSDK_SUCCESS)
		{
			OEM_LOGE(" adjust rtc time failed %d!\n", status);
			goto _fail;
		}
	}
	else if(SetTime_Flag == 2)
	{
		OEM_LOGI("UE will adjust rtc time\r\n");
		rtc_time.rtc_year = DeviceConfig.Time_Year;
		rtc_time.rtc_mon  = DeviceConfig.Time_Mon;
		rtc_time.rtc_day  = DeviceConfig.Time_Mday;
		rtc_time.rtc_hour = DeviceConfig.Time_Hour;
		rtc_time.rtc_min  = DeviceConfig.Time_Min;
		rtc_time.rtc_sec  = DeviceConfig.Time_Sec;

		status = gsdk_rtc_time_write(rtc_handle, &rtc_time);
		if (status != GSDK_SUCCESS)
		{
			OEM_LOGE(" adjust rtc time failed %d!\n", status);
			goto _fail;
		}
	}
	return 1;

_fail:
	OEM_LOGI("[RTC_DEMO] RTC_Timing failed!\n");
	gsdk_rtc_close(rtc_handle);
	return -1;
}

/*******************************************************************************
* Function Name  : Set_Alarm
* Description    : RTC设置闹钟
* Input          : long  SleepPara,休眠时间,为0时不设置闹钟直接休眠
* Output         : none
* Return         : 1成功,0失败
*******************************************************************************/
void Set_Alarm(long  SleepPara)
{
	gsdk_status_t status;
	int i,j;
	gsdk_handle_t g_alarm_handle;
    uint8_t count = 0;

	if(SleepPara > 0)
	{
		/*configure alarm timer property*/
		gsdk_alarm_config_t alarm_config;
		alarm_config.callback = rtc_alarm_cb;//timer callback
		alarm_config.interval = SleepPara-30;//单位:s
		alarm_config.periodic = 1;//timer perform periodically
		status = gsdk_alarm_open(&g_alarm_handle, &alarm_config);//open alarm timer
		if (status != GSDK_SUCCESS)
		{
			DEBUG_LOG("open alarm  failed :%d\r\n", status);			
			goto _fail;
		}
		WARN_LOG("open alarm success\r\n");
		status = gsdk_alarm_start(g_alarm_handle);//start up alarm timer
		if (status != GSDK_SUCCESS)
		{
			DEBUG_LOG("gsdk_alarm_start failed :%d\r\n", status);
			goto _fail;
		}
		WARN_LOG("start alarm success\r\n");
	}
	gsdk_rtc_close(rtc_handle);

	for(i=0; i<3; i++)
	{
		status = gsdk_ril_psm_set(CPSMS, "AT+CPSMS=1");//set "CPSMS=1" is power saving mode(PSM)
		if(GSDK_ERROR == status)
		{
			DEBUG_LOG("set CPSMS=1 cmd error\r\n");
			goto _fail;
		}
		WARN_LOG("set CPSM=1 cmd success\r\n");

		status = gsdk_ril_psm_set(ZSLR, "AT+ZSLR");//sleep command
		if(GSDK_ERROR == status)
		{
			DEBUG_LOG("set ZSLR cmd error\r\n");
			goto _fail;
		}

		WARN_LOG("wait for sleep....\r\n");
		for(j=0; j<3; j++)
		{
			DEBUG_LOG("-->ME3616 IS SLEEP <--\r\n");
			while (1)
			{
				if (count > 20)
				{
					break;
				}
				vTaskDelay(500 / portTICK_PERIOD_MS);
				count++;
			}			
//			vTaskDelay(1000);                           //延时10S,等待睡眠
			DEBUG_LOG("-->ME3616 IS WAKE <--\r\n");
		}
	}

	gsdk_ril_set_hardware_reboot();

_fail:
	WARN_LOG("Set_Alarm fail....\r\n");
	gsdk_ril_reset_module();
}

/*******************************************************************************
* Function Name  : Get_Boot_Mode
* Description    : 获取NB模块启动模式
* Input          : long  SleepPara,休眠时间,为0时不设置闹钟直接休眠
* Output         : none
* Return         : Boot_Mode_Flag
*******************************************************************************/
uint8_t Get_Boot_Mode(void)
{
	gsdk_boot_mode_t boot_mode;
	gsdk_rtc_wakeup_mode_t wakeup_mode;
	uint8_t Boot_Mode_Flag = 0;

	/*get boot mode function ,because this demo maybe enter PSM */
	boot_mode = gsdk_sys_get_boot_mode(&wakeup_mode);
	DEBUG_LOG("boot_mode is---------------------------------------------- :%d\r\n", boot_mode);
	if (1 == boot_mode || 2 == boot_mode)
	{
//        printf("wakeup from deep sleep\r\n");
		switch (wakeup_mode)
		{
		case GSDK_BOOT_RTC_TC_WAKEUP:
			WARN_LOG("it's awakened by RTC_TC\r\n");
			break;
		case GSDK_BOOT_RTC_EINT_WAKEUP:
			WARN_LOG("it's awakened by RTC_EINT\r\n");
			break;
		case GSDK_BOOT_RTC_ALARM_WAKEUP:
			WARN_LOG("it's awakened by ALARM_WAKEUP\r\n");
			Boot_Mode_Flag = 1;
			break;
		case GSDK_BOOT_POWERKEY_WAKEUP:
			WARN_LOG("it's awakened by POWERKEY\r\n");
			break;
		default:
			WARN_LOG("unknown mode\r\n");
			break;
		}
	}
	else if (5 == boot_mode || 6 == boot_mode)
	{
		Boot_Mode_Flag = 3;
		WARN_LOG("GSDK_BOOT_WDT_SW_RESET\r\n");
	}
	else
	{
		Boot_Mode_Flag = 2;
		WARN_LOG("not enter deep sleep\r\n");
	}
	return Boot_Mode_Flag;
}