Files

633 lines
18 KiB
C

#include "pmoc_comm.h"
#include "drv_pmc.h"
#include <linux/rtc.h>
#include "xmedia_errcode.h"
#include "mmz.h"
extern int lotus_rtc_aov_read_time(struct device *dev, struct rtc_time *time, unsigned char *ms_count);
extern int lotus_rtc_aov_set_alarm_time(struct device *dev, unsigned int alarm_time, unsigned char alarm_enable);
extern int pm_set_aux_src(void __iomem *aux_src, unsigned long size);
extern int lotus_rtc_aov_get_resume_time(struct device *dev, struct rtc_time *time, unsigned char *ms_count);
extern int lotus_rtc_aov_get_suspend_time(struct device *dev, struct rtc_time *time, unsigned char *ms);
extern int lotus_rtc_aov_get_current_time(struct device *dev, struct rtc_time *time, unsigned char *ms);
static xmedia_void *virt_pwr_base_addr = XMEDIA_NULL;
#ifdef CONFIG_PM
static xmedia_void *virt_aux_store_addr = XMEDIA_NULL;
#endif
struct mutex pmc_mutex;
xmedia_s32 lotus_pmc_init(xmedia_void)
{
virt_pwr_base_addr = osal_ioremap(PWR_BASE_ADDR, 0x40);
if (virt_pwr_base_addr == XMEDIA_NULL) {
PM_TRACE(MODULE_DBG_ERR, "lotus_pmc_init ioremap err!\n");
return XMEDIA_ERRCODE_BAD_ADDRESS;
}
mutex_init(&pmc_mutex);
return XMEDIA_SUCCESS;
}
xmedia_s32 lotus_pmc_set_aux(struct aux_mem *aux)
{
#ifdef CONFIG_PM
if (virt_aux_store_addr != XMEDIA_NULL) {
PM_TRACE(MODULE_DBG_ERR, "%s aux is exist!\n", __func__);
return XMEDIA_ERRCODE_EXIST;
}
virt_aux_store_addr = mmz_map(aux->phy_addr, aux->size, 0);
if (virt_aux_store_addr == NULL) {
PM_TRACE(MODULE_DBG_ERR, "%s addr 0x%llx mmap error!\n", __func__, aux->phy_addr);
return XMEDIA_ERRCODE_NOT_ENOUGH_MEMORY;
}
pm_set_aux_src(virt_aux_store_addr, aux->size);
return XMEDIA_SUCCESS;
#else
return XMEDIA_ERRCODE_NOT_SUPPORT;
#endif
}
xmedia_void lotus_pmc_deinit(xmedia_void)
{
if (virt_pwr_base_addr != XMEDIA_NULL) {
osal_iounmap(virt_pwr_base_addr);
virt_pwr_base_addr = XMEDIA_NULL;
}
#ifdef CONFIG_PM
if (virt_aux_store_addr != XMEDIA_NULL) {
mmz_unmap(virt_aux_store_addr);
pm_set_aux_src(0, 0);
virt_aux_store_addr = NULL;
}
#endif
}
xmedia_s32 lotus_get_wakeup_type(lotus_pmc_wakeup_type *type)
{
xmedia_u32 status;
xmedia_s32 ret = XMEDIA_SUCCESS;
if (virt_pwr_base_addr == XMEDIA_NULL) {
PM_TRACE(MODULE_DBG_ERR, "pmc not init err!\n");
return XMEDIA_ERRCODE_BAD_ADDRESS;
}
if (type == XMEDIA_NULL) {
PM_TRACE(MODULE_DBG_ERR, "set_wakeup_attr parameter err!\n");
return XMEDIA_ERRCODE_NULL_PTR;
}
status = osal_readl(virt_pwr_base_addr + PMR_STATUS_OFFSET);
status &= PWR_STATUS_WAKEUP_SOURCE;
status >>= 2;
switch (status) {
case 1:
*type = PMC_SRC_WAKEUP;
break;
case 4:
*type = PMC_SRC_STARTUP;
break;
case 8:
*type = PMC_SRC_BUTTON;
break;
case 16:
*type = PMC_SRC_RTC;
break;
default:
*type = PMC_SRC_MAX;
ret = XMEDIA_FAILURE;
break;
}
return ret;
}
#ifdef PM_WAKEUP1_SUPPORT
xmedia_s32 lotus_pm_get_wakeup_info(lotus_pm_wakeup_info *info)
{
xmedia_s32 ret = XMEDIA_SUCCESS;
xmedia_u32 status;
xmedia_u32 wakeup0_crtl, wakeup1_crtl;
ret = lotus_get_wakeup_type(&info->type);
if (ret)
return ret;
if (info->type == PMC_SRC_WAKEUP) {
wakeup0_crtl = osal_readl(virt_pwr_base_addr + PWR_WAKEUP_CRTL_OFFSET);
wakeup1_crtl = osal_readl(virt_pwr_base_addr + PWR_WAKEUP1_CRTL_OFFSET);
/* wakeup0 and wakeup1 is both enable */
if (((wakeup0_crtl & PWR_WAKEUPN_IOSHARE) == 0) && ((wakeup1_crtl & PWR_WAKEUPN_IOSHARE) == 0)) {
status = osal_readl(virt_pwr_base_addr + PWR_STATUS_BACKUP_OFFSET);
if (status & WAKEUP_STATUS_GPIO0_MASK)
info->detail = 0;
else if (status & WAKEUP_STATUS_GPIO1_MASK)
info->detail = 1;
else {
info->detail = 0;
PM_TRACE(MODULE_DBG_ERR, "wakeup int happened, but do not find gpio wakeup status!\n");
ret = XMEDIA_FAILURE;
}
/* wakeup1 is only enabled */
} else if ((wakeup1_crtl & PWR_WAKEUPN_IOSHARE) == 0) {
info->detail = 1;
} else if ((wakeup0_crtl & PWR_WAKEUPN_IOSHARE) == 0) {
info->detail = 0;
} else {
info->detail = 0;
PM_TRACE(MODULE_DBG_ERR, "wakeup int happened, but do not find gpio wakeup config!\n");
ret = XMEDIA_ERRCODE_NOT_CONFIG;
}
} else {
info->detail = 0;
}
return ret;
}
static xmedia_s32 lotus_config_wakeup_gpio(lotus_pmc_all_attr *attr)
{
xmedia_u32 value;
if (attr->wakeup_attr.wakeup_enable && attr->wakeup_ext_attr_arry[0].wakeup_enable) {
if (attr->wakeup_attr.wakeup_polarity != PMC_PWR_HIGH_LEVEL || attr->wakeup_ext_attr_arry[0].wakeup_polarity != PMC_PWR_HIGH_LEVEL)
return XMEDIA_ERRCODE_NOT_SUPPORT;
}
if (!attr->wakeup_attr.wakeup_enable) {
value = osal_readl(virt_pwr_base_addr + PWR_WAKEUP_CRTL_OFFSET);
value |= PWR_WAKEUPN_IOSHARE;
osal_writel(value, virt_pwr_base_addr + PWR_WAKEUP_CRTL_OFFSET);
} else if (attr->wakeup_attr.wakeup_polarity == PMC_PWR_HIGH_LEVEL ||
attr->wakeup_attr.wakeup_polarity == PMC_PWR_RISING_EDGE) {
value = osal_readl(virt_pwr_base_addr + PWR_WAKEUP_CRTL_OFFSET);
value &= ~PWR_WAKEUPN_IOSHARE;
/* pull down */
value |= PWR_WAKEUP_PD;
/* do not pull up */
value &= ~PWR_WAKEUP_PU;
/* driver strength level2 */
value &= ~PWR_WAKEUP_DS_MASK;
value |= PWR_WAKEUP_DS_2;
osal_writel(value, virt_pwr_base_addr + PWR_WAKEUP_CRTL_OFFSET);
} else {
value = osal_readl(virt_pwr_base_addr + PWR_WAKEUP_CRTL_OFFSET);
value &= ~PWR_WAKEUPN_IOSHARE;
/* do not pull down */
value &= ~PWR_WAKEUP_PD;
/* pull up */
value |= PWR_WAKEUP_PU;
/* driver strength level2 */
value &= ~PWR_WAKEUP_DS_MASK;
value |= PWR_WAKEUP_DS_2;
osal_writel(value, virt_pwr_base_addr + PWR_WAKEUP_CRTL_OFFSET);
}
if (!attr->wakeup_ext_attr_arry[0].wakeup_enable) {
value = osal_readl(virt_pwr_base_addr + PWR_WAKEUP1_CRTL_OFFSET);
value |= PWR_WAKEUPN_IOSHARE;
osal_writel(value, virt_pwr_base_addr + PWR_WAKEUP1_CRTL_OFFSET);
} else if (attr->wakeup_ext_attr_arry[0].wakeup_polarity == PMC_PWR_HIGH_LEVEL ||
attr->wakeup_ext_attr_arry[0].wakeup_polarity == PMC_PWR_RISING_EDGE) {
value = osal_readl(virt_pwr_base_addr + PWR_WAKEUP1_CRTL_OFFSET);
value &= ~PWR_WAKEUPN_IOSHARE;
/* pull down */
value |= PWR_WAKEUP_PD;
/* do not pull up */
value &= ~PWR_WAKEUP_PU;
/* driver strength level2 */
value &= ~PWR_WAKEUP_DS_MASK;
value |= PWR_WAKEUP_DS_2;
osal_writel(value, virt_pwr_base_addr + PWR_WAKEUP1_CRTL_OFFSET);
} else {
value = osal_readl(virt_pwr_base_addr + PWR_WAKEUP1_CRTL_OFFSET);
value &= ~PWR_WAKEUPN_IOSHARE;
/* do not pull down */
value &= ~PWR_WAKEUP_PD;
/* pull up */
value |= PWR_WAKEUP_PU;
/* driver strength level2 */
value &= ~PWR_WAKEUP_DS_MASK;
value |= PWR_WAKEUP_DS_2;
osal_writel(value, virt_pwr_base_addr + PWR_WAKEUP1_CRTL_OFFSET);
}
return XMEDIA_SUCCESS;
}
#else
static xmedia_s32 lotus_config_wakeup_gpio(lotus_pmc_all_attr *attr)
{
xmedia_u32 value;
if (!attr->wakeup_attr.wakeup_enable) {
value = osal_readl(virt_pwr_base_addr + PWR_WAKEUP_CRTL_OFFSET);
value |= PWR_WAKEUPN_IOSHARE;
osal_writel(value, virt_pwr_base_addr + PWR_WAKEUP_CRTL_OFFSET);
} else if (attr->wakeup_attr.wakeup_polarity == PMC_PWR_HIGH_LEVEL ||
attr->wakeup_attr.wakeup_polarity == PMC_PWR_RISING_EDGE) {
value = osal_readl(virt_pwr_base_addr + PWR_WAKEUP_CRTL_OFFSET);
value &= ~PWR_WAKEUPN_IOSHARE;
/* pull down */
value |= PWR_WAKEUP_PD;
/* do not pull up */
value &= ~PWR_WAKEUP_PU;
/* driver strength level2 */
value &= ~PWR_WAKEUP_DS_MASK;
value |= PWR_WAKEUP_DS_2;
osal_writel(value, virt_pwr_base_addr + PWR_WAKEUP_CRTL_OFFSET);
} else {
value = osal_readl(virt_pwr_base_addr + PWR_WAKEUP_CRTL_OFFSET);
value &= ~PWR_WAKEUPN_IOSHARE;
/* do not pull down */
value &= ~PWR_WAKEUP_PD;
/* pull up */
value |= PWR_WAKEUP_PU;
/* driver strength level2 */
value &= ~PWR_WAKEUP_DS_MASK;
value |= PWR_WAKEUP_DS_2;
osal_writel(value, virt_pwr_base_addr + PWR_WAKEUP_CRTL_OFFSET);
}
value = osal_readl(virt_pwr_base_addr + PWR_WAKEUP1_CRTL_OFFSET);
value |= PWR_WAKEUPN_IOSHARE;
osal_writel(value, virt_pwr_base_addr + PWR_WAKEUP1_CRTL_OFFSET);
return XMEDIA_SUCCESS;
}
#endif
xmedia_s32 lotus_set_all_attr(lotus_pmc_all_attr *attr)
{
xmedia_s32 ret = XMEDIA_SUCCESS;
if (virt_pwr_base_addr == XMEDIA_NULL) {
PM_TRACE(MODULE_DBG_ERR, "pmc not init err!\n");
return XMEDIA_ERRCODE_BAD_ADDRESS;
}
if (attr == XMEDIA_NULL) {
PM_TRACE(MODULE_DBG_ERR, "set_wakeup_attr parameter err!\n");
return XMEDIA_ERRCODE_NULL_PTR;
}
ret = lotus_config_wakeup_gpio(attr);
if (ret != XMEDIA_SUCCESS) {
return ret;
}
#ifdef PM_WAKEUP1_SUPPORT
if ((!attr->wakeup_attr.wakeup_enable) && attr->wakeup_ext_attr_arry[0].wakeup_enable)
ret = lotus_set_wakeup_attr(&(attr->wakeup_ext_attr_arry[0]));
else
ret = lotus_set_wakeup_attr(&(attr->wakeup_attr));
#else
ret = lotus_set_wakeup_attr(&(attr->wakeup_attr));
#endif
if (ret != XMEDIA_SUCCESS) {
return ret;
}
ret = lotus_set_button_attr(&(attr->button_attr));
if (ret != XMEDIA_SUCCESS) {
return ret;
}
ret = lotus_set_rtc_attr(&(attr->rtc_attr));
if (ret != XMEDIA_SUCCESS) {
return ret;
}
return XMEDIA_SUCCESS;
}
xmedia_s32 lotus_get_all_attr(lotus_pmc_all_attr *attr)
{
xmedia_s32 ret = XMEDIA_SUCCESS;
if (virt_pwr_base_addr == XMEDIA_NULL) {
PM_TRACE(MODULE_DBG_ERR, "pmc not init err!\n");
return XMEDIA_ERRCODE_BAD_ADDRESS;
}
if (attr == XMEDIA_NULL) {
PM_TRACE(MODULE_DBG_ERR, "set_wakeup_attr parameter err!\n");
return XMEDIA_ERRCODE_NULL_PTR;
}
attr->startup_enable = 1;
attr->button_enable = 1;
ret = lotus_get_wakeup_attr(&(attr->wakeup_attr));
if (ret != XMEDIA_SUCCESS) {
return ret;
}
ret = lotus_get_button_attr(&(attr->button_attr));
if (ret != XMEDIA_SUCCESS) {
return ret;
}
ret = lotus_get_rtc_attr(&(attr->rtc_attr));
if (ret != XMEDIA_SUCCESS) {
return ret;
}
return XMEDIA_SUCCESS;
}
xmedia_s32 lotus_set_wakeup_attr(lotus_pmc_wakeup_attr *attr)
{
xmedia_u32 status;
if (virt_pwr_base_addr == XMEDIA_NULL) {
PM_TRACE(MODULE_DBG_ERR, "set_Wakeup_attr parameter err!\n");
return XMEDIA_ERRCODE_BAD_ADDRESS;
}
if (attr == XMEDIA_NULL) {
PM_TRACE(MODULE_DBG_ERR, "set_Wakeup_attr parameter err!\n");
return XMEDIA_ERRCODE_NULL_PTR;
}
mutex_lock(&pmc_mutex);
status = osal_readl(virt_pwr_base_addr + PWR_CTRL0_OFFSET);
status &= ~PWR_POWER_UNMASK;
if (attr->wakeup_enable == 1) {
osal_writel(status & ~PWR_WAKEUP_MASK, (virt_pwr_base_addr + PWR_CTRL0_OFFSET));
} else {
osal_writel(status | PWR_WAKEUP_MASK, (virt_pwr_base_addr + PWR_CTRL0_OFFSET));
}
if (attr->wakeup_polarity < PMC_PWR_MAX) {
status = osal_readl(virt_pwr_base_addr + PWR_CTRL0_OFFSET);
status &= ~PWR_WAKEUP_POLARITY;
status |= (attr->wakeup_polarity << 3);
osal_writel(status, (virt_pwr_base_addr + PWR_CTRL0_OFFSET));
} else {
mutex_unlock(&pmc_mutex);
PM_TRACE(MODULE_DBG_ERR, "set_Wakeup_attr parameter err!\n");
return XMEDIA_ERRCODE_INVALID_PARAM;
}
mutex_unlock(&pmc_mutex);
PM_TRACE(MODULE_DBG_INFO, "set_wakeup_attr success!\n");
return XMEDIA_SUCCESS;
}
xmedia_s32 lotus_get_wakeup_attr(lotus_pmc_wakeup_attr *attr)
{
xmedia_u32 status;
if (virt_pwr_base_addr == XMEDIA_NULL) {
PM_TRACE(MODULE_DBG_ERR, "pmc not init err!\n");
return XMEDIA_ERRCODE_BAD_ADDRESS;
}
if (attr == XMEDIA_NULL) {
PM_TRACE(MODULE_DBG_ERR, "get_wakeup_attr parameter err!\n");
return XMEDIA_ERRCODE_NULL_PTR;
}
status = osal_readl(virt_pwr_base_addr + PWR_CTRL0_OFFSET);
status &=~ PWR_POWER_UNMASK;
attr->wakeup_enable = !((status & PWR_WAKEUP_MASK) >> 6);
attr->wakeup_polarity = (status & PWR_WAKEUP_POLARITY) >> 3;
PM_TRACE(MODULE_DBG_INFO, "get_wakeup_attr success!\n");
return XMEDIA_SUCCESS;
}
xmedia_s32 lotus_set_button_attr(lotus_pmc_button_attr *attr)
{
xmedia_u32 status;
if (virt_pwr_base_addr ==XMEDIA_NULL) {
PM_TRACE(MODULE_DBG_ERR, "set_button_attr parameter err!\n");
return XMEDIA_ERRCODE_BAD_ADDRESS;
}
if (attr == XMEDIA_NULL) {
PM_TRACE(MODULE_DBG_ERR, "set_button_attr parameter err!\n");
return XMEDIA_ERRCODE_NULL_PTR;
}
mutex_lock(&pmc_mutex);
status = osal_readl(virt_pwr_base_addr + PWR_CTRL0_OFFSET);
status &=~ PWR_POWER_UNMASK;
if (attr->button_adj_enable == 1) {
osal_writel(status &~ PWR_BUTTON_ADJ_MASK, (virt_pwr_base_addr + PWR_CTRL0_OFFSET));
if (attr->button_adj_time <= PWR_BUTTON_ADJ_TIME_MAX) {
status = osal_readl(virt_pwr_base_addr + PWR_CTRL0_OFFSET);
status &=~ PWR_POWER_UNMASK;
status &=~ PWR_BUTTON_ADJ_TIME_MASK;
status |= (attr->button_adj_time << PWR_BUTTON_ADJ_TIME_SHIFT);
osal_writel(status, (virt_pwr_base_addr + PWR_CTRL0_OFFSET));
} else {
mutex_unlock(&pmc_mutex);
PM_TRACE(MODULE_DBG_ERR, "set_button_adjust_time parameter err!\n");
return XMEDIA_ERRCODE_INVALID_PARAM;
}
} else {
osal_writel(status | PWR_BUTTON_ADJ_MASK, (virt_pwr_base_addr + PWR_CTRL0_OFFSET));
}
mutex_unlock(&pmc_mutex);
PM_TRACE(MODULE_DBG_INFO, "set_button_adjust_time success!\n");
return XMEDIA_SUCCESS;
}
xmedia_s32 lotus_get_button_attr(lotus_pmc_button_attr *attr)
{
xmedia_u32 status;
if (virt_pwr_base_addr == XMEDIA_NULL) {
PM_TRACE(MODULE_DBG_ERR, "pmc not init err!\n");
return XMEDIA_ERRCODE_BAD_ADDRESS;
}
if (attr == XMEDIA_NULL) {
PM_TRACE(MODULE_DBG_ERR, "get_button_attr parameter err!\n");
return XMEDIA_ERRCODE_NULL_PTR;
}
status = osal_readl(virt_pwr_base_addr + PWR_CTRL0_OFFSET);
status &=~ PWR_POWER_UNMASK;
attr->button_adj_enable = !((status & PWR_BUTTON_ADJ_MASK) >> PWR_BUTTON_ADJ_MASK_SHIFT);
attr->button_adj_time = (status & PWR_BUTTON_ADJ_TIME_MASK) >> PWR_BUTTON_ADJ_TIME_SHIFT;
PM_TRACE(MODULE_DBG_INFO, "get_button_adjust_time success!\n");
return XMEDIA_SUCCESS;
}
xmedia_s32 lotus_set_rtc_attr(lotus_pmc_rtc_attr *attr)
{
xmedia_u32 status;
struct rtc_device *dev;
struct rtc_wkalrm alarm = {0};
xmedia_u32 ret;
if (virt_pwr_base_addr == XMEDIA_NULL) {
PM_TRACE(MODULE_DBG_ERR, "pmc not init err!\n");
return XMEDIA_ERRCODE_BAD_ADDRESS;
}
if (attr == XMEDIA_NULL) {
PM_TRACE(MODULE_DBG_ERR, "set_wakeup_attr parameter err!\n");
return XMEDIA_ERRCODE_NULL_PTR;
}
status = osal_readl(virt_pwr_base_addr + PWR_CTRL0_OFFSET);
status &=~ PWR_POWER_UNMASK;
if (attr->rtc_enable == 1) {
osal_writel(status & ~PWR_RTC_MASK, (virt_pwr_base_addr + PWR_CTRL0_OFFSET));
dev = rtc_class_open("rtc0");
if (dev == XMEDIA_NULL) {
goto rtc_failure;
}
ret = rtc_read_alarm(dev, &alarm);
if (ret != XMEDIA_SUCCESS) {
goto rtc_failure;
}
PM_TRACE(MODULE_DBG_DEBUG, "rtc_read_alarm start: %d-%d-%d-%d-%d-%d, %d-%d-%d\n", alarm.time.tm_year, \
alarm.time.tm_mon, alarm.time.tm_mday, alarm.time.tm_hour, alarm.time.tm_min, alarm.time.tm_sec, alarm.time.tm_year, alarm.time.tm_yday, alarm.time.tm_isdst);
lotus_rtc_aov_set_alarm_time(dev->dev.parent, attr->rtc_timeout, 1);
rtc_class_close(dev);
} else {
osal_writel(status | PWR_RTC_MASK, (virt_pwr_base_addr + PWR_CTRL0_OFFSET));
}
PM_TRACE(MODULE_DBG_INFO, "set_rtc_attr success!\n");
return XMEDIA_SUCCESS;
rtc_failure:
PM_TRACE(MODULE_DBG_ERR, "set rtc timeout failure!\n");
return XMEDIA_FAILURE;
}
xmedia_s32 lotus_get_rtc_attr(lotus_pmc_rtc_attr *attr)
{
xmedia_u32 status;
if (virt_pwr_base_addr == XMEDIA_NULL) {
PM_TRACE(MODULE_DBG_ERR, "pmc not init err!\n");
return XMEDIA_ERRCODE_BAD_ADDRESS;
}
if (attr == XMEDIA_NULL) {
PM_TRACE(MODULE_DBG_ERR, "set_wakeup_attr parameter err!\n");
return XMEDIA_ERRCODE_NULL_PTR;
}
status = osal_readl(virt_pwr_base_addr + PWR_CTRL0_OFFSET);
status &=~ PWR_POWER_UNMASK;
attr->rtc_enable = !((status & PWR_RTC_MASK) >> 5);;
attr->rtc_timeout = 0;
PM_TRACE(MODULE_DBG_INFO, "get_rtc_attr success!\n");
return XMEDIA_SUCCESS;
}
xmedia_s32 lotus_pm_get_rtc_info(lotus_pm_rtc_info *info)
{
struct rtc_device *dev;
struct rtc_time linuxTime = {0};
unsigned char ms_count;
int ret = XMEDIA_SUCCESS;
time64_t seconds = 0;
dev = rtc_class_open("rtc0");
if (dev == XMEDIA_NULL) {
return XMEDIA_ERRCODE_OPEN_FAILED;
}
ret = lotus_rtc_aov_get_resume_time(dev->dev.parent, &linuxTime, &ms_count);
if (ret != 0) {
PM_TRACE(MODULE_DBG_INFO, "rtc get resume time fail: 0x%X\n", ret);
goto out;
}
seconds = rtc_tm_to_time64(&linuxTime);
info->rtc_delta_time = seconds * 1000 + ms_count * 10;
PM_TRACE(MODULE_DBG_INFO, "get rtc resume time: %d-%d-%d %d:%d:%d.%d \n", linuxTime.tm_year, linuxTime.tm_mon, linuxTime.tm_mday, linuxTime.tm_hour, linuxTime.tm_min, linuxTime.tm_sec, ms_count * 10);
ret = lotus_rtc_aov_get_suspend_time(dev->dev.parent, &linuxTime, &ms_count);
if (ret != 0) {
PM_TRACE(MODULE_DBG_INFO, "rtc get resume time fail: 0x%X\n", ret);
goto out;
}
seconds = rtc_tm_to_time64(&linuxTime);
info->rtc_last_suspend_time = seconds * 1000 + ms_count * 10;
PM_TRACE(MODULE_DBG_INFO, "get rtc suspend time: %d-%d-%d %d:%d:%d.%d \n", linuxTime.tm_year, linuxTime.tm_mon, linuxTime.tm_mday, linuxTime.tm_hour, linuxTime.tm_min, linuxTime.tm_sec, ms_count * 10);
ret = lotus_rtc_aov_get_current_time(dev->dev.parent, &linuxTime, &ms_count);
if (ret != 0) {
PM_TRACE(MODULE_DBG_INFO, "rtc get resume time fail: 0x%X\n", ret);
goto out;
}
seconds = rtc_tm_to_time64(&linuxTime);
info->rtc_current_time = seconds * 1000 + ms_count * 10;
PM_TRACE(MODULE_DBG_INFO, "get rtc current time: %d-%d-%d %d:%d:%d.%d \n", linuxTime.tm_year, linuxTime.tm_mon, linuxTime.tm_mday, linuxTime.tm_hour, linuxTime.tm_min, linuxTime.tm_sec, ms_count * 10);
out:
if (dev)
rtc_class_close(dev);
return ret;
}
xmedia_void lotus_get_rtc_timer(xmedia_void)
{
struct rtc_device *dev;
struct rtc_time linuxTime = {0};
unsigned char ms_count;
dev = rtc_class_open("rtc0");
if (dev == XMEDIA_NULL) {
return;
}
lotus_rtc_aov_read_time(dev->dev.parent, &linuxTime, &ms_count);
rtc_class_close(dev);
osal_printk("get rtc timer:%d:%d:%d \n", linuxTime.tm_min, linuxTime.tm_sec, ms_count);
}