[processor-sdk/pdk.git] / packages / ti / drv / pa / example / multicoreExample / src / c66x / bios / framework.c
1 /**\r
2 * @file framework.c\r
3 *\r
4 * @brief\r
5 * This file holds all the platform specific framework\r
6 * initialization and setup code.\r
7 *\r
8 * \par\r
9 * ============================================================================\r
10 * @n (C) Copyright 2009-2013, Texas Instruments, Inc.\r
11 *\r
12 * Redistribution and use in source and binary forms, with or without\r
13 * modification, are permitted provided that the following conditions\r
14 * are met:\r
15 *\r
16 * Redistributions of source code must retain the above copyright\r
17 * notice, this list of conditions and the following disclaimer.\r
18 *\r
19 * Redistributions in binary form must reproduce the above copyright\r
20 * notice, this list of conditions and the following disclaimer in the\r
21 * documentation and/or other materials provided with the\r
22 * distribution.\r
23 *\r
24 * Neither the name of Texas Instruments Incorporated nor the names of\r
25 * its contributors may be used to endorse or promote products derived\r
26 * from this software without specific prior written permission.\r
27 *\r
28 * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS\r
29 * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT\r
30 * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR\r
31 * A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT\r
32 * OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,\r
33 * SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT\r
34 * LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,\r
35 * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY\r
36 * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT\r
37 * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE\r
38 * OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.\r
39 *\r
40 */\r
41 #include "multicore_example.h"\r
42 \r
43 #include <ti/csl/cslr_device.h>\r
44 #include <ti/csl/csl_psc.h>\r
45 #include <ti/csl/csl_pscAux.h>\r
46 \r
47 /* PASS RL file */\r
48 #include <ti/csl/cslr_device.h>\r
49 #include <ti/csl/cslr_pa_ss.h>\r
50 \r
51 /* Firmware images */\r
52 #include <ti/drv/pa/fw/pafw.h>\r
53 \r
54 /** ============================================================================\r
55 * @n@b Convert_CoreLocal2GlobalAddr\r
56 *\r
57 * @b Description\r
58 * @n This API converts a core local L2 address to a global L2 address.\r
59 *\r
60 * @param[in]\r
61 * @n addr L2 address to be converted to global.\r
62 *\r
63 * @return UInt32\r
64 * @n >0 Global L2 address\r
65 * =============================================================================\r
66 */\r
67 UInt32 Convert_CoreLocal2GlobalAddr (UInt32 addr)\r
68 {\r
69 uint32_t coreNum;\r
70 \r
71 /* Get the core number. */\r
72 coreNum = CSL_chipReadReg(CSL_CHIP_DNUM);\r
73 \r
74 /* Compute the global address. */\r
75 return ((1 << 28) | (coreNum << 24) | (addr & 0x00ffffff));\r
76 }\r
77 \r
78 /** ============================================================================\r
79 * @n@b Convert_CoreGlobal2L2Addr\r
80 *\r
81 * @b Description\r
82 * @n This API converts a core local L2 address to a global L2 address.\r
83 *\r
84 * @param[in]\r
85 * @n addr L2 address to be converted to global.\r
86 *\r
87 * @return uint32_t\r
88 * @n >0 Global L2 address\r
89 * =============================================================================\r
90 */\r
91 uint32_t Convert_CoreGlobal2L2Addr (uint32_t addr)\r
92 {\r
93 /* Compute the local l2 address. */\r
94 return (addr & 0x00ffffff);\r
95 }\r
96 \r
97 /** ============================================================================\r
98 * @n@b get_qmssGblCfgParamsRegsPhy2Virt\r
99 *\r
100 * @b Description\r
101 * @n This API updates the QMSS global configuration registers to global\r
102 * addressable space for that platform.\r
103 *\r
104 * @param[in]\r
105 * @n addr L2 address to be converted to global.\r
106 *\r
107 * @return uint32_t\r
108 * @n >0 Global L2 address\r
109 * =============================================================================\r
110 */\r
111 void get_qmssGblCfgParamsRegsPhy2Virt(Qmss_GlobalConfigParams *fw_qmssGblCfgParams)\r
112 {\r
113 /* Since all physical memory is accessible in DSP, nothing to be done */\r
114 return;\r
115 }\r
116 \r
117 /** ============================================================================\r
118 * @n@b get_cppiGblCfgParamsRegsPhy2Virt\r
119 *\r
120 * @b Description\r
121 * @n This API updates the QMSS global configuration registers to global\r
122 * addressable space for that platform.\r
123 *\r
124 * @param[in]\r
125 * @n addr L2 address to be converted to global.\r
126 *\r
127 * @return uint32_t\r
128 * @n >0 Global L2 address\r
129 * =============================================================================\r
130 */\r
131 void get_cppiGblCfgParamsRegsPhy2Virt(Cppi_GlobalConfigParams *fw_cppiGblCfgParams)\r
132 {\r
133 /* Since all physical memory is accessible in DSP, nothing to be done */\r
134 return;\r
135 }\r
136 \r
137 /***************************************************************************************\r
138 * FUNCTION PURPOSE: Power up PA subsystem\r
139 ***************************************************************************************\r
140 * DESCRIPTION: this function powers up the PA subsystem domains\r
141 ***************************************************************************************/\r
142 void passPowerUp (void)\r
143 {\r
144 \r
145 /* PASS power domain is turned OFF by default. It needs to be turned on before doing any\r
146 * PASS device register access. This not required for the simulator. */\r
147 \r
148 /* Set PASS Power domain to ON */\r
149 CSL_PSC_enablePowerDomain (CSL_PSC_PD_NETCP);\r
150 \r
151 /* Enable the clocks for PASS modules */\r
152 CSL_PSC_setModuleNextState (CSL_PSC_LPSC_PA, PSC_MODSTATE_ENABLE);\r
153 CSL_PSC_setModuleNextState (CSL_PSC_LPSC_CPGMAC, PSC_MODSTATE_ENABLE);\r
154 CSL_PSC_setModuleNextState (CSL_PSC_LPSC_SA, PSC_MODSTATE_ENABLE);\r
155 \r
156 /* Start the state transition */\r
157 CSL_PSC_startStateTransition (CSL_PSC_PD_NETCP);\r
158 \r
159 /* Wait until the state transition process is completed. */\r
160 while (!CSL_PSC_isStateTransitionDone (CSL_PSC_PD_NETCP));\r
161 }\r
162 \r
163 \r
164 void CycleDelay (int32_t count)\r
165 {\r
166 uint32_t TSCLin;\r
167 \r
168 if (count <= 0)\r
169 return;\r
170 \r
171 /* Get the current TSCL */\r
172 TSCLin = TSCL ;\r
173 \r
174 while ((TSCL - TSCLin) < (uint32_t)count);\r
175 }\r
176 \r
177 void APP_exit (int32_t code)\r
178 {\r
179 BIOS_exit(code);\r
180 }\r
181 \r
182 void APP_publishGlobalCfgDone(void)\r
183 {\r
184 /* Store all global handles in the shared memory and Publish the config is done */\r
185 fw_shmSetEntry();\r
186 \r
187 }\r
188 \r
189 void APP_waitGlobalCfgDone(void)\r
190 {\r
191 uint32_t globalCfgDone;\r
192 pa_Example_shmStr_e shm;\r
193 \r
194 shm = globalCfgDoneAddr;\r
195 do {\r
196 globalCfgDone = (uint32_t) fw_shmGetEntry(shm);\r
197 } while(!globalCfgDone);\r
198 }\r
199 \r
200 /* Huge memory block reserved for shared memory use */\r
201 #pragma DATA_ALIGN (mem_blk_shm, CACHE_LINESZ)\r
202 #pragma DATA_SECTION (mem_blk_shm, ".sharedDDR")\r
203 uint8_t mem_blk_shm[pa_Example_MC_SHM_SIZE];\r
204 \r
205 int32_t fw_shmDelete(void)\r
206 {\r
207 return 0;\r
208 }\r
209 \r
210 void APP_readAllHndles(void)\r
211 {\r
212 gTxFreeQHnd = (Qmss_QueueHnd) fw_shmGetEntry(gTxFreeQHndAddr);\r
213 gRxFreeQHnd = (Qmss_QueueHnd) fw_shmGetEntry(gRxFreeQHndAddr);\r
214 //gCpdmaHnd = (Cppi_Handle) fw_shmGetEntry(gCpdmaHndAddr);\r
215 gPAInstHnd = (Pa_Handle) fw_shmGetEntry(gPAInstHndAddr);\r
216 gPaL2Handles = (paHandleL2L3_t)fw_shmGetEntry(gPaL2HandlesAddr);\r
217 gPaL3Handles = (paHandleL2L3_t)fw_shmGetEntry(gPaL3HandlesAddr);\r
218 }\r
219 \r
220 uint32_t fw_shmGetEntry(pa_Example_shmStr_e shmstr)\r
221 {\r
222 uint32_t addr;\r
223 \r
224 switch (shmstr)\r
225 {\r
226 case gTxFreeQHndAddr:\r
227 SYS_CACHE_INV ((void *) &shObj->gTxFreeQHnd, 128, CACHE_WAIT);\r
228 addr = (uint32_t) shObj->gTxFreeQHnd;\r
229 break;\r
230 case gRxFreeQHndAddr:\r
231 SYS_CACHE_INV ((void *) &shObj->gRxFreeQHnd, 128, CACHE_WAIT);\r
232 addr = (uint32_t) shObj->gRxFreeQHnd;\r
233 break;\r
234 case gCpdmaHndAddr :\r
235 SYS_CACHE_INV ((void *) &shObj->gCpdmaHnd, 128, CACHE_WAIT);\r
236 addr = (uint32_t) shObj->gCpdmaHnd;\r
237 break;\r
238 case gPAInstHndAddr:\r
239 SYS_CACHE_INV ((void *) &shObj->gPAInstHnd, 128, CACHE_WAIT);\r
240 addr = (uint32_t) shObj->gPAInstHnd;\r
241 break;\r
242 case gPaL2HandlesAddr:\r
243 SYS_CACHE_INV ((void *) &shObj->gPaL2Handles, 128, CACHE_WAIT);\r
244 addr = (uint32_t) shObj->gPaL2Handles;\r
245 break;\r
246 case gPaL3HandlesAddr:\r
247 SYS_CACHE_INV ((void *) &shObj->gPaL3Handles, 128, CACHE_WAIT);\r
248 addr = (uint32_t) shObj->gPaL3Handles;\r
249 break;\r
250 case globalCfgDoneAddr:\r
251 SYS_CACHE_INV ((void *) &shObj->globalCfgDone, 128, CACHE_WAIT);\r
252 addr = (uint32_t) shObj->globalCfgDone;\r
253 break;\r
254 case localCfgDoneAddr:\r
255 SYS_CACHE_INV ((void *) &shObj->localCfgDone, 128, CACHE_WAIT);\r
256 addr = (uint32_t) shObj->localCfgDone;\r
257 break;\r
258 case localTestDoneAddr:\r
259 SYS_CACHE_INV ((void *) &shObj->localTestDone, 128, CACHE_WAIT);\r
260 addr = (uint32_t) shObj->localTestDone;\r
261 break;\r
262 case allPktRxCntAddr:\r
263 SYS_CACHE_INV ((void *) &shObj->allPktRxCnt, 128, CACHE_WAIT);\r
264 addr = (uint32_t) shObj->allPktRxCnt;\r
265 break;\r
266 case gPaInstBufAddr:\r
267 addr = (uint32_t) shObj->gPAInst;\r
268 break;\r
269 case gMemL2RamBufAddr:\r
270 addr = (uint32_t) shObj->gMemL2Ram;\r
271 break;\r
272 case gMemL3RamBufAddr:\r
273 addr = (uint32_t) shObj->gMemL3Ram;\r
274 break;\r
275 case gMemUsrStatsBufAddr:\r
276 addr = (uint32_t) shObj->gMemUsrStats;\r
277 break;\r
278 case gPaInstBufSize:\r
279 addr = (uint32_t) sizeof (shObj->gPAInst);\r
280 break;\r
281 case gMemL2RamBufSize:\r
282 addr = (uint32_t) sizeof (shObj->gMemL2Ram);\r
283 break;\r
284 case gMemL3RamBufSize:\r
285 addr = (uint32_t) sizeof (shObj->gMemL3Ram);\r
286 break;\r
287 case gMemUsrStatsBufSize:\r
288 addr = (uint32_t) sizeof (shObj->gMemUsrStats);\r
289 break;\r
290 default:\r
291 addr = (uint32_t) NULL;\r
292 break;\r
293 }\r
294 \r
295 return (addr);\r
296 }\r
297 \r
298 /* Note that this function needs to be called by Master Core only */\r
299 void fw_shmSetEntry(void)\r
300 {\r
301 uint32_t* addr;\r
302 \r
303 addr = (uint32_t*) &shObj->gTxFreeQHnd;\r
304 *addr = (uint32_t) gTxFreeQHnd;\r
305 SYS_CACHE_WB ((void *) addr, 128, CACHE_WAIT);\r
306 \r
307 addr = (uint32_t *) &shObj->gRxFreeQHnd;\r
308 *addr = (uint32_t) gRxFreeQHnd;\r
309 SYS_CACHE_WB ((void *) addr, 128, CACHE_WAIT);\r
310 \r
311 addr = (uint32_t *) &shObj->gCpdmaHnd;\r
312 *addr = (uint32_t) gCpdmaHnd;\r
313 SYS_CACHE_WB ((void *) addr, 128, CACHE_WAIT);\r
314 \r
315 addr = (uint32_t *) &shObj->gPAInstHnd;\r
316 *addr = (uint32_t) gPAInstHnd;\r
317 SYS_CACHE_WB ((void *) addr, 128, CACHE_WAIT);\r
318 \r
319 addr = (uint32_t *) &shObj->gPaL2Handles;\r
320 *addr = (uint32_t) gPaL2Handles;\r
321 SYS_CACHE_WB ((void *) addr, 128, CACHE_WAIT);\r
322 \r
323 addr = (uint32_t *) &shObj->gPaL3Handles;\r
324 *addr = (uint32_t) gPaL3Handles;\r
325 SYS_CACHE_WB ((void *) addr, 128, CACHE_WAIT);\r
326 \r
327 addr = (uint32_t *) &shObj->globalCfgDone;\r
328 *addr = TRUE;\r
329 SYS_CACHE_WB ((void *) addr, 128, CACHE_WAIT);\r
330 \r
331 }\r
332 \r
333 void fw_shmCreate(void)\r
334 {\r
335 uint32_t coreNum;\r
336 /* Get the core number. */\r
337 coreNum = CSL_chipReadReg(CSL_CHIP_DNUM);\r
338 \r
339 if (coreNum == SYSINIT)\r
340 {\r
341 memset(mem_blk_shm, 0, sizeof (mem_blk_shm));\r
342 SYS_CACHE_WB ((void *) mem_blk_shm, sizeof (mem_blk_shm), CACHE_WAIT);\r
343 shObj = (pa_Example_MC_ShObj_t*) mem_blk_shm;\r
344 }\r
345 \r
346 }\r
347 \r
348 void fw_shmOpen(void)\r
349 {\r
350 shObj = (pa_Example_MC_ShObj_t*) mem_blk_shm;\r
351 }\r
352 \r
353 void fw_shmClose(void)\r
354 {\r
355 shObj = (pa_Example_MC_ShObj_t*) NULL;\r
356 }\r
357 \r
358 void APP_publishLocalCfgDone(void)\r
359 {\r
360 uint32_t* addr;\r
361 \r
362 while ((CSL_semAcquireDirect (PA_APP_HW_SEM_SYS)) == 0);\r
363 \r
364 addr = (uint32_t *) &shObj->localCfgDone;\r
365 *addr += 1;\r
366 SYS_CACHE_WB ((void *) addr, 128, CACHE_WAIT);\r
367 \r
368 /* Release the hardware semaphore. */\r
369 CSL_semReleaseSemaphore (PA_APP_HW_SEM_SYS);\r
370 }\r
371 \r
372 void APP_waitAllLocalCfgDone(void)\r
373 {\r
374 uint32_t localCfgDone;\r
375 \r
376 do {\r
377 localCfgDone = (uint32_t) fw_shmGetEntry(localCfgDoneAddr);\r
378 } while (localCfgDone != pa_MC_EXAMPLE_NUM_CORES);\r
379 }\r
380 \r
381 \r
382 void APP_publishLocalTestDone(void)\r
383 {\r
384 uint32_t* addr;\r
385 \r
386 while ((CSL_semAcquireDirect (PA_APP_HW_SEM_SYS)) == 0);\r
387 \r
388 addr = (uint32_t *) &shObj->localTestDone;\r
389 *addr += 1;\r
390 SYS_CACHE_WB ((void *) addr, 128, CACHE_WAIT);\r
391 \r
392 /* Release the hardware semaphore. */\r
393 CSL_semReleaseSemaphore (PA_APP_HW_SEM_SYS);\r
394 }\r
395 \r
396 void APP_waitAllLocalTestDone(void)\r
397 {\r
398 uint32_t localCfgDone;\r
399 \r
400 do {\r
401 localCfgDone = (uint32_t) fw_shmGetEntry(localTestDoneAddr);\r
402 } while (localCfgDone != pa_MC_EXAMPLE_NUM_CORES);\r
403 }\r
404 \r
405 int32_t APP_checkTestStatus(void)\r
406 {\r
407 uint32_t testRxCnt;\r
408 \r
409 testRxCnt = (uint32_t) fw_shmGetEntry(allPktRxCntAddr);\r
410 \r
411 return (testRxCnt == pa_MC_EXAMPLE_NUM_CORES);\r
412 }\r
413 \r
414 \r
415 void APP_publishTestStatus(void)\r
416 {\r
417 uint32_t* addr;\r
418 \r
419 /* wait for the semaphore */\r
420 while ((CSL_semAcquireDirect (PA_APP_HW_SEM_SYS)) == 0);\r
421 \r
422 addr = (uint32_t *) &shObj->allPktRxCnt;\r
423 *addr += 1;\r
424 SYS_CACHE_WB ((void *) addr, CACHE_LINESZ, CACHE_WAIT);\r
425 \r
426 /* Release the hardware semaphore. */\r
427 CSL_semReleaseSemaphore (PA_APP_HW_SEM_SYS);\r
428 \r
429 }\r
430 \r
431 /** ============================================================================\r
432 * @n@b initRm\r
433 *\r
434 * @b Description\r
435 * @n This API initializes the RM Client for the QMSS test establishing\r
436 * a socket connection with the RM Server\r
437 * \r
438 * @return int32_t\r
439 * -1 - Error\r
440 * 0 - Success\r
441 * =============================================================================\r
442 */\r
443 int initRm (void)\r
444 {\r
445 #if RM && !defined(__LINUX_USER_SPACE)\r
446 int32_t rmResult;\r
447 #endif /* RM */\r
448 \r
449 #if RM\r
450 rmClientServiceHandle = Rm_serviceOpenHandle(rmHandle, &rmResult);\r
451 if (rmResult != RM_OK)\r
452 {\r
453 System_printf ("Error Core %d : Creating RM service handle error code : %d\n", coreNum, rmResult);\r
454 return -1;\r
455 }\r
456 #endif /* RM */\r
457 return 0;\r
458 \r
459 }\r
460 \r
461 /* Nothing past this point */\r