1 /** mbed Microcontroller Library
2   ******************************************************************************
3   * @file    sys_api.c
4   * @author
5   * @version V1.0.0
6   * @date    2016-08-01
7   * @brief   This file provides following mbed system API:
8   *				-JTAG OFF
9   *				-LOGUART ON/OFF
10   *				-OTA image switch
11   *				-System Reset
12   ******************************************************************************
13   * @attention
14   *
15   * This module is a confidential and proprietary property of RealTek and
16   * possession or use of this module requires written permission of RealTek.
17   *
18   * Copyright(c) 2016, Realtek Semiconductor Corporation. All rights reserved.
19   ******************************************************************************
20   */
21 
22 #include "cmsis.h"
23 #include "sys_api.h"
24 #include "flash_api.h"
25 #include "device_lock.h"
26 #include "rtl8721d_ota.h"
27 
28 void rtc_backup_timeinfo(void);
29 
30 //#define printf					DiagPrintf
31 
32 /** @addtogroup AmebaD_Mbed_API
33   * @{
34   */
35 
36 /** @defgroup MBED_SYSAPI
37  *  @brief      MBED_SYSAPI driver modules.
38  *  @{
39  */
40 
41 /** @defgroup MBED_SYSAPI_Exported_Functions MBED_SYSAPI Exported Functions
42   * @{
43   */
44 
45 /**
46   * @brief  Turn off the JTAG function
47   * @retval none
48   */
sys_jtag_off(void)49 void sys_jtag_off(void)
50 {
51 	Pinmux_Swdoff();
52 }
53 
54 /**
55   * @brief  clear the signature of current firmware
56   * @retval none
57   */
sys_clear_ota_signature(void)58 void sys_clear_ota_signature(void)
59 {
60 	u32 AddrStart, Offset, IsMinus, PhyAddr;
61 	u32 FwAddr;
62 	u8 EmpSig = 0;
63 
64 	RSIP_REG_TypeDef* RSIP = ((RSIP_REG_TypeDef *) RSIP_REG_BASE);
65 	u32 CtrlTemp = RSIP->FLASH_MMU[0].MMU_ENTRYx_CTRL;
66 
67 	if (CtrlTemp & MMU_BIT_ENTRY_VALID) {
68 		AddrStart = RSIP->FLASH_MMU[0].MMU_ENTRYx_STRADDR;
69 		Offset = RSIP->FLASH_MMU[0].MMU_ENTRYx_OFFSET;
70 		IsMinus = CtrlTemp & MMU_BIT_ENTRY_OFFSET_MINUS;
71 
72 		if(IsMinus)
73 			PhyAddr = AddrStart - Offset;
74 		else
75 			PhyAddr = AddrStart + Offset;
76 
77 		if(PhyAddr == LS_IMG2_OTA1_ADDR)
78 			FwAddr = LS_IMG2_OTA1_ADDR;
79 		else
80 			FwAddr = LS_IMG2_OTA2_ADDR;
81 	}
82 
83 	FLASH_WriteStream(FwAddr - SPI_FLASH_BASE, 4, &EmpSig);
84 }
85 
86 /**
87   * @brief  recover the signature of the other firmware
88   * @retval none
89   */
sys_recover_ota_signature(void)90 void sys_recover_ota_signature(void)
91 {
92 	u32 AddrStart, Offset, IsMinus, PhyAddr;
93 	u8 Ota2Use = _FALSE;
94 	u32 DstAddr, CurAddr;
95 	u8 OldSig, NewSig;
96 	u8 *buf;
97 
98 	RSIP_REG_TypeDef* RSIP = ((RSIP_REG_TypeDef *) RSIP_REG_BASE);
99 	u32 CtrlTemp = RSIP->FLASH_MMU[0].MMU_ENTRYx_CTRL;
100 
101 	/* Get which firmware used */
102 	if (CtrlTemp & MMU_BIT_ENTRY_VALID) {
103 		AddrStart = RSIP->FLASH_MMU[0].MMU_ENTRYx_STRADDR;
104 		Offset = RSIP->FLASH_MMU[0].MMU_ENTRYx_OFFSET;
105 		IsMinus = CtrlTemp & MMU_BIT_ENTRY_OFFSET_MINUS;
106 
107 		if(IsMinus)
108 			PhyAddr = AddrStart - Offset;
109 		else
110 			PhyAddr = AddrStart + Offset;
111 
112 		if(PhyAddr == LS_IMG2_OTA1_ADDR)
113 			Ota2Use = _FALSE;
114 		else
115 			Ota2Use = _TRUE;
116 	}
117 
118 	if(Ota2Use) {
119 		CurAddr = LS_IMG2_OTA2_ADDR;
120 		DstAddr = LS_IMG2_OTA1_ADDR;
121 	} else {
122 		CurAddr = LS_IMG2_OTA1_ADDR;
123 		DstAddr = LS_IMG2_OTA2_ADDR;
124 	}
125 
126 	/* Get signature of the two firmware */
127 	ota_readstream_user(DstAddr, 4, &OldSig);
128 	ota_readstream_user(CurAddr, 4, &NewSig);
129 	DBG_8195A("old sig: %08x, new sig:%08x\n", OldSig, NewSig);
130 
131 	if(OldSig == NewSig) {
132 		return;
133 	}
134 
135 	/* Backup first 4KB of the old firmware */
136 	buf = pvPortMalloc(4096);
137 	ota_readstream_user(DstAddr, 4096, buf);
138 
139 	/* Modify signature */
140 	_memcpy(buf, &NewSig, 4);
141 
142 	/* Erase first sector */
143 	flash_erase_sector(NULL, DstAddr);
144 
145 	/* Write back 4KB to first sector */
146 	flash_stream_write(NULL, DstAddr, 4096, buf);
147 
148 	vPortFree(buf);
149 }
150 
151 /**
152   * @brief  open log uart
153   * @retval none
154   */
sys_log_uart_on(void)155 void sys_log_uart_on(void)
156 {
157 	/* Just Support S0 */
158 	Pinmux_UartLogCtrl(PINMUX_S0, ON);
159 
160 	UART_INTConfig(UART2_DEV, RUART_IER_ERBI, ENABLE);
161 	UART_RxCmd(UART2_DEV, ENABLE);
162 }
163 
164 /**
165   * @brief  close log uart
166   * @retval none
167   */
sys_log_uart_off(void)168 void sys_log_uart_off(void)
169 {
170 	UART_INTConfig(UART2_DEV, RUART_IER_ERBI, DISABLE);
171 	UART_RxCmd(UART2_DEV, DISABLE);
172 
173 	/* Just Support S0 */
174 	Pinmux_UartLogCtrl(PINMUX_S0, OFF);
175 }
176 
177 
178 /**
179   * @brief  store or load adc calibration parameter
180   * @param  write:  this parameter can be one of the following values:
181   *		@arg 0: load adc calibration parameter offset & gain
182   *		@arg 1: store adc calibration parameter offset & gain
183   * @param  offset: pointer to adc parameter offset
184   * @param  gain: pointer to adc parameter gain
185   * @retval none
186   */
sys_adc_calibration(u8 write,u16 * offset,u16 * gain)187 void sys_adc_calibration(u8 write, u16 *offset, u16 *gain)
188 {
189 	/* To avoid gcc warnings */
190 	( void ) write;
191 	( void ) offset;
192 	( void ) gain;
193 
194 	printf("ADC calibration is finished in FT test. Calibration parameters can be found in EFUSE." \
195 		"Please refer to Battery Measurement chapter in Application Note to get calibration parameters.\n");
196 
197 	assert_param(0);
198 }
199 
200 /**
201   * @brief  system software reset
202   * @retval none
203   */
sys_reset(void)204 void sys_reset(void)
205 {
206 	WDG_InitTypeDef WDG_InitStruct;
207 	u32 CountProcess;
208 	u32 DivFacProcess;
209 
210 	rtc_backup_timeinfo();
211 
212 	WDG_Scalar(50, &CountProcess, &DivFacProcess);
213 	WDG_InitStruct.CountProcess = CountProcess;
214 	WDG_InitStruct.DivFacProcess = DivFacProcess;
215 	WDG_Init(&WDG_InitStruct);
216 
217 	WDG_Cmd(ENABLE);
218 }
219 
220 
221 /**
222   * @brief vector reset
223   * @retval none
224   */
sys_cpu_reset(void)225 void sys_cpu_reset(void)
226 {
227 #ifdef AMEBAD_TODO
228 	u32 reg_value;
229 
230 	rtc_backup_timeinfo();
231 
232 	reg_value = HAL_READ32(PERI_ON_BASE, REG_SOC_FUNC_EN);
233 	reg_value |= BIT_SOC_PATCH_FUNC1;
234 	HAL_WRITE32(PERI_ON_BASE, REG_SOC_FUNC_EN, reg_value);
235 
236 	/* Ensure all outstanding memory accesses included */
237 	/* buffered write are completed before reset */
238 	__DSB();
239 
240 	/* CPU reset */
241 	/* Keep priority group unchanged */
242 	SCB->AIRCR  = ((0x5FA << SCB_AIRCR_VECTKEY_Pos) |
243 		(SCB->AIRCR & SCB_AIRCR_PRIGROUP_Msk) |
244 		SCB_AIRCR_VECTRESET_Pos | SCB_AIRCR_VECTCLRACTIVE_Pos);
245 
246 	/* Ensure completion of memory access */
247 	__DSB();
248 
249 	while(1);
250 #endif
251 }
252 /**
253   * @}
254   */
255 
256 /**
257   * @}
258   */
259 
260 /**
261   * @}
262   */
263 
264 /******************* (C) COPYRIGHT 2016 Realtek Semiconductor *****END OF FILE****/
265