Include licencing terms in the source files themselves.
[open-ath9k-htc-firmware.git] / target_firmware / magpie_fw_dev / target / init / init.c
1 /*
2  * Copyright (c) 2013 Qualcomm Atheros, Inc.
3  * All rights reserved.
4  *
5  * Redistribution and use in source and binary forms, with or without
6  * modification, are permitted (subject to the limitations in the
7  * disclaimer below) provided that the following conditions are met:
8  *
9  *  * Redistributions of source code must retain the above copyright
10  *    notice, this list of conditions and the following disclaimer.
11  *
12  *  * Redistributions in binary form must reproduce the above copyright
13  *    notice, this list of conditions and the following disclaimer in the
14  *    documentation and/or other materials provided with the
15  *    distribution.
16  *
17  *  * Neither the name of Qualcomm Atheros nor the names of its
18  *    contributors may be used to endorse or promote products derived
19  *    from this software without specific prior written permission.
20  *
21  * NO EXPRESS OR IMPLIED LICENSES TO ANY PARTY'S PATENT RIGHTS ARE
22  * GRANTED BY THIS LICENSE.  THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT
23  * HOLDERS AND CONTRIBUTORS "AS IS" AND ANY EXPRESS OR IMPLIED
24  * WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF
25  * MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
26  * DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR CONTRIBUTORS BE
27  * LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
28  * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
29  * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR
30  * BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY,
31  * WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE
32  * OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN
33  * IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
34  */
35 #if defined(_RAM_)
36
37 #include "athos_api.h"
38     
39 #if defined(PROJECT_MAGPIE)
40 #include "regdump.h"
41 #include "usb_defs.h"
42 extern  uint32_t *init_htc_handle;
43 uint8_t htc_complete_setup = 0;
44 void reset_EP4_FIFO(void);
45 #endif
46 #include "init.h"
47
48 void Magpie_init(void);
49
50
51 #if defined(PROJECT_MAGPIE)
52 extern BOOLEAN bEepromExist;
53 extern BOOLEAN bJumptoFlash;
54 #endif
55
56 static uint32_t loop_low, loop_high;
57
58 // reference idle count at the beginning
59 uint32_t idle_cnt = 0;
60
61 #if defined(PROJECT_K2)
62 // save the ROM printf function point
63 uint32_t save_cmnos_printf;
64 #endif
65
66 #define ATH_DATE_STRING     __DATE__" "__TIME__
67
68 static void idle_task();
69
70 #if defined(PROJECT_MAGPIE)
71 void fatal_exception_func()
72 {
73         // patch for execption
74         (void)_xtos_set_exception_handler(EXCCAUSE_UNALIGNED, AR6002_fatal_exception_handler_patch);
75         (void)_xtos_set_exception_handler(EXCCAUSE_LOAD_STORE_ERROR, AR6002_fatal_exception_handler_patch);
76         (void)_xtos_set_exception_handler(EXCCAUSE_ILLEGAL, AR6002_fatal_exception_handler_patch);
77         (void)_xtos_set_exception_handler(EXCCAUSE_INSTR_ERROR, AR6002_fatal_exception_handler_patch);
78         (void)_xtos_set_exception_handler(EXCCAUSE_PRIVILEGED, AR6002_fatal_exception_handler_patch);
79         (void)_xtos_set_exception_handler(EXCCAUSE_INSTR_DATA_ERROR, AR6002_fatal_exception_handler_patch);
80         (void)_xtos_set_exception_handler(EXCCAUSE_LOAD_STORE_DATA_ERROR, AR6002_fatal_exception_handler_patch);
81         (void)_xtos_set_exception_handler(EXCCAUSE_DIVIDE_BY_ZERO, AR6002_fatal_exception_handler_patch);
82 }
83 #endif
84
85 #if defined(PROJECT_MAGPIE)
86 void
87 change_magpie_clk(void)
88 {
89         volatile uint32_t i=0, rd_data;
90
91         HAL_WORD_REG_WRITE(0x00056004, 0x11);
92         rd_data = HAL_WORD_REG_READ(0x00056004) & 0x1;
93
94         /* Wait for the update bit to get cleared */
95         while (rd_data)
96                 rd_data = HAL_WORD_REG_READ(0x00056004) & 0x1;
97
98         /* Put the PLL into reset */
99         rd_data = HAL_WORD_REG_READ(0x00050010) | (1<<1);
100         HAL_WORD_REG_WRITE(0x00050010,rd_data);
101
102         /*
103          * XXX: statically set the CPU clock to 200Mhz
104          */
105         /* Setting of the PLL */
106         HAL_WORD_REG_WRITE(0x00056000, 0x325);//400 MHz
107
108         /* Pull CPU PLL out of Reset */
109         rd_data = HAL_WORD_REG_READ(0x00050010) & ~(1<<1);
110         HAL_WORD_REG_WRITE(0x00050010,rd_data);
111
112         A_DELAY_USECS(60); // wait for stable
113
114         /* CPU & AHB settings */  
115         /*
116          * AHB clk = ( CPU clk / 2 )
117          */
118         HAL_WORD_REG_WRITE(0x00056004, ((0x00001 | (1 << 16)|(1 << 8)))); // set plldiv to 2
119         rd_data = HAL_WORD_REG_READ(0x00056004) & 0x1;
120
121         while (rd_data)
122                 rd_data = HAL_WORD_REG_READ(0x00056004) & 0x1;
123
124         /* UART Setting */
125         A_UART_HWINIT((100*1000*1000), 115200);
126
127 }
128
129 void exception_reset(struct register_dump_s *dump)
130 {
131         A_PRINTF("exception_reset \n");
132
133         /* phase I dump info */
134         A_PRINTF("exception reset-phase 1\n");
135         if(_assfail_ori)
136                 _assfail_ori(dump);
137
138         /* phase II reset */
139         A_PRINTF("exception reset-phase 2\n");
140         *((volatile uint32_t*)WATCH_DOG_MAGIC_PATTERN_ADDR) = WDT_MAGIC_PATTERN;
141
142         HAL_WORD_REG_WRITE(MAGPIE_REG_RST_RESET_ADDR, 
143                            HAL_WORD_REG_READ(MAGPIE_REG_RST_RESET_ADDR)|(BIT10|BIT8|BIT7|BIT6));
144
145         HAL_WORD_REG_WRITE(MAGPIE_REG_AHB_ARB_ADDR,
146                            (HAL_WORD_REG_READ(MAGPIE_REG_AHB_ARB_ADDR)|BIT1));
147
148         HAL_WORD_REG_WRITE((USB_CTRL_BASE_ADDRESS+0x118), 0x0);
149         HAL_WORD_REG_WRITE(0x50010, HAL_WORD_REG_READ(0x50010)|BIT4);
150         A_DELAY_USECS(5);
151         HAL_WORD_REG_WRITE(0x50010, HAL_WORD_REG_READ(0x50010)&~BIT4);
152         A_DELAY_USECS(5);
153         HAL_WORD_REG_WRITE((USB_CTRL_BASE_ADDRESS+0x118), 0x1);
154
155         // set clock to bypass mode - 40Mhz from XTAL
156         HAL_WORD_REG_WRITE(MAGPIE_REG_CPU_PLL_BYPASS_ADDR, (BIT0|BIT4));
157         A_DELAY_USECS(100); // wait for stable
158         HAL_WORD_REG_WRITE(MAGPIE_REG_CPU_PLL_ADDR, (BIT16));
159
160         A_UART_HWINIT((40*1000*1000), 115200);
161
162         A_PRINTF("do TX/RX swap\n");
163
164         MAGPIE_REG_USB_RX0_SWAP_DATA = 0x1;
165         MAGPIE_REG_USB_TX0_SWAP_DATA = 0x1;
166         MAGPIE_REG_USB_RX1_SWAP_DATA = 0x1;
167         MAGPIE_REG_USB_RX2_SWAP_DATA = 0x1;
168
169         A_PRINTF("Jump to BOOT\n");
170
171         // reboot.....
172         A_USB_JUMP_BOOT();
173 }
174
175 void reset_EP4_FIFO(void)
176 {
177         int i;
178
179         // reset EP4 FIFO
180         USB_BYTE_REG_WRITE(ZM_EP4_BYTE_COUNT_HIGH_OFFSET, (USB_BYTE_REG_READ(ZM_EP4_BYTE_COUNT_HIGH_OFFSET) | BIT4));
181         for(i = 0; i < 100; i++) {}
182         USB_BYTE_REG_WRITE(ZM_EP4_BYTE_COUNT_HIGH_OFFSET, (USB_BYTE_REG_READ(ZM_EP4_BYTE_COUNT_HIGH_OFFSET) & ~BIT4)); 
183 }
184
185 LOCAL void zfGenExceptionEvent(uint32_t exccause, uint32_t pc, uint32_t badvaddr)
186 {
187         uint32_t pattern = 0x33221199;
188
189         A_PRINTF("<Exception>Tgt Drv send an event 44332211 to Host Drv\n");
190         mUSB_STATUS_IN_INT_DISABLE();
191
192         USB_WORD_REG_WRITE(ZM_CBUS_FIFO_SIZE_OFFSET, 0x0f);
193
194         USB_WORD_REG_WRITE(ZM_EP3_DATA_OFFSET, pattern);
195         USB_WORD_REG_WRITE(ZM_EP3_DATA_OFFSET, exccause);
196         USB_WORD_REG_WRITE(ZM_EP3_DATA_OFFSET, pc);
197         USB_WORD_REG_WRITE(ZM_EP3_DATA_OFFSET, badvaddr);
198     
199         mUSB_EP3_XFER_DONE();
200 }
201
202 LOCAL void zfGenWrongEpidEvent(uint32_t epid)
203 {
204         uint32_t pattern   = 0x33221299;
205
206         A_PRINTF("<WrongEPID>Tgt Drv send an event 44332212 to Host Drv\n");
207         mUSB_STATUS_IN_INT_DISABLE();
208
209         USB_WORD_REG_WRITE(ZM_CBUS_FIFO_SIZE_OFFSET, 0x0f);
210
211         USB_WORD_REG_WRITE(ZM_EP3_DATA_OFFSET, pattern);
212         USB_WORD_REG_WRITE(ZM_EP3_DATA_OFFSET, epid);
213
214         mUSB_EP3_XFER_DONE();
215 }
216
217 void
218 AR6002_fatal_exception_handler_patch(CPU_exception_frame_t *exc_frame)
219 {
220         struct register_dump_s dump;
221         void (*reset_func)(void) = (void*)(RESET_VECTOR_ADDRESS);
222         uint32_t  exc_cause, exc_vaddr;
223         asm volatile("rsr %0,%1" : "=r" (exc_cause) : "n" (EXCCAUSE));
224         asm volatile("rsr %0,%1" : "=r" (exc_vaddr) : "n" (EXCVADDR));
225
226         dump.exc_frame              = *exc_frame; /* structure copy */
227         dump.badvaddr               = exc_vaddr;
228         dump.exc_frame.xt_exccause  = exc_cause;
229         dump.pc                     = exc_frame->xt_pc;
230         dump.assline                = 0;
231
232         zfGenExceptionEvent(dump.exc_frame.xt_exccause, dump.pc, dump.badvaddr);
233
234 #if SYSTEM_MODULE_PRINT
235         A_PRINTF("\nFatal exception (%d): \tpc=0x%x \n\r\tbadvaddr=0x%x \n\r\tdump area=0x%x\n",
236                  dump.exc_frame.xt_exccause, dump.pc, dump.badvaddr, &dump);
237         PRINT_FAILURE_STATE();
238 #else
239         A_PUTS("Fatal exception\n\r");
240 #endif
241         A_ASSFAIL(&dump);
242
243 #if defined(_ROM_)     
244         A_WDT_ENABLE();
245 #endif
246
247         while(1) ;
248 }
249
250 void 
251 HTCControlSvcProcessMsg_patch(HTC_ENDPOINT_ID EndpointID, adf_nbuf_t hdr_buf,
252                               adf_nbuf_t pBuffers, void *arg)
253 {
254         a_uint8_t *anbdata;
255         a_uint32_t anblen;
256         HTC_UNKNOWN_MSG *pMsg;
257
258         /* we assume buffers are aligned such that we can access the message
259          * parameters directly*/
260         adf_nbuf_peek_header(pBuffers, &anbdata, &anblen);
261         pMsg = (HTC_UNKNOWN_MSG *)anbdata;
262
263         if (pMsg->MessageID == HTC_MSG_SETUP_COMPLETE_ID) {
264                 htc_complete_setup = 1;
265         }
266
267         HTCControlSvcProcessMsg(EndpointID, hdr_buf, pBuffers, arg);
268 }
269
270 /* Patch callback for check the endpoint ID is correct or not */
271 void 
272 HTCMsgRecvHandler_patch(adf_nbuf_t hdr_buf, adf_nbuf_t buffer, void *context)
273 {
274         int eid;
275         a_uint8_t *anbdata;
276         a_uint32_t anblen;
277         adf_nbuf_t tmp_nbuf;
278         HTC_FRAME_HDR *pHTCHdr;
279                 
280         if (hdr_buf == ADF_NBUF_NULL) {
281                 /* HTC hdr is not in the hdr_buf */
282                 tmp_nbuf = buffer;
283         } else {
284                 tmp_nbuf = hdr_buf;
285         }
286                 
287         adf_nbuf_peek_header(tmp_nbuf, &anbdata, &anblen);        
288         pHTCHdr = (HTC_FRAME_HDR *)anbdata; 
289   
290         eid = pHTCHdr->EndpointID;
291     
292         if ((eid != 0) && (htc_complete_setup == 0)) {
293                 A_PRINTF("\nHTC Hdr EndpointID = %d, anblen = %d\n", pHTCHdr->EndpointID, anblen);
294                 A_PRINTF("HTC Hder : %2x-%2x-%2x-%2x-%2x-%2x-%2x-%2x-%2x-%2x-%2x-%2x\n",
295                          *anbdata, *(anbdata+1), *(anbdata+2), *(anbdata+3), 
296                          *(anbdata+4), *(anbdata+5), *(anbdata+6), *(anbdata+7),
297                          *(anbdata+8), *(anbdata+9), *(anbdata+10), *(anbdata+11)); 
298                 A_PRINTF("init_htc_handle = 0x%8x\n", init_htc_handle);
299             
300                 if (pHTCHdr->EndpointID == 1) {
301                         A_PRINTF("Return WMI Command buffer\n");
302                         HTC_ReturnBuffers(init_htc_handle, 1, tmp_nbuf);
303                 } else if ((pHTCHdr->EndpointID == 5) || (pHTCHdr->EndpointID == 6)) {
304                         A_PRINTF("Return Data buffer\n");
305                         HTC_ReturnBuffers(init_htc_handle, 6, tmp_nbuf);
306                 } else {
307                 }
308         } else {
309                 if ((pHTCHdr->EndpointID < 0) || (pHTCHdr->EndpointID >= ENDPOINT_MAX)) {
310                         A_PRINTF("HTC Hdr EndpointID = %d, anblen = %d\n", pHTCHdr->EndpointID, anblen);
311                         A_PRINTF("HTC Hder : %2x-%2x-%2x-%2x-%2x-%2x-%2x-%2x\n", 
312                                  *anbdata, *(anbdata+1), *(anbdata+2), *(anbdata+3), 
313                                  *(anbdata+4), *(anbdata+5), *(anbdata+6), *(anbdata+7));
314
315                         if (anblen > 64) {
316                                 A_PRINTF("EP1-Tx-Data with Wrong Htc Header Endpoint ID, WAR free this buffer\n");
317                                 HTC_ReturnBuffers(init_htc_handle, 6, tmp_nbuf);
318                                 A_PRINTF("EP1-Tx-Data > Free this buffer successfully\n");
319                         } else {
320                                 A_PRINTF("EP4-WMI-Cmd with Wrong Htc Header Endpoint ID, WAR free this buffer\n");
321                                 zfGenWrongEpidEvent((a_uint32_t)pHTCHdr->EndpointID);
322                                 HTC_ReturnBuffers(init_htc_handle, 1, tmp_nbuf);
323                                 A_PRINTF("EP4-WMI-Cmd > Free this buffer successfully\n");
324                         }
325                 } else
326                         HTCMsgRecvHandler( hdr_buf, buffer, context);
327         }
328 }
329 #endif
330
331 void init_mem()
332 {
333         int i = 0;
334         uint32_t *temp = (uint32_t *)ALLOCRAM_START;
335
336         /* clear bss segment */
337         for(temp = (uint32_t *)&START_BSS; temp < (uint32_t *)&END_BSS; temp++)
338                 *temp = 0;
339
340         /* clear heap segment */
341         for(i = 0; i < ((ALLOCRAM_SIZE - 4)/4); i++)
342                 temp[i] = 0;
343 }
344
345 static void idle_task()
346 {
347         if (loop_low == 0xffffffff) {
348                 loop_low = 0;
349                 loop_high++;
350         } else {
351                 loop_low++;
352         }
353         return;
354 }
355
356 void wlan_task(void)
357 {
358         loop_low=loop_high=0;
359
360         while(1) {
361 #if defined(PROJECT_MAGPIE)
362                 if (bJumptoFlash){
363                         bJumptoFlash = FALSE;
364                         break;
365                 }
366 #endif
367
368                 /* update wdt timer */
369                 A_WDT_TASK();
370
371                 /* UPDATE cticks - to be moved to idle_tsk, put here will be easier to read  */
372                 A_CLOCK_TICK();
373
374                 HIF_isr_handler(NULL);
375
376 #if MAGPIE_ENABLE_WLAN == 1
377                 wlan_pci_isr();
378 #endif
379
380                 A_TASKLET_RUN();
381                 A_TIMER_RUN();
382
383                 /* Low priority tasks */
384                 if ((loop_low & 0xf) == 0) {
385                 }
386
387                 /* Very low priority tasks */
388                 if ((loop_low & 0xfff) == 0x7) {
389                         if ((loop_low & 0x1000) == 0) {
390                                 A_DBG_TASK();
391                         } else {
392                         }
393                 }
394
395                 idle_task();
396         }
397 }
398
399 #endif /* #if defined(_RAM_) */