Added EMAC loopback support and updated projects to use resource manager
[keystone-rtos/mcsdk-tools.git] / post / src / post.c
1 /******************************************************************************
2  * Copyright (c) 2011 Texas Instruments Incorporated - http://www.ti.com
3  *
4  *  Redistribution and use in source and binary forms, with or without
5  *  modification, are permitted provided that the following conditions
6  *  are met:
7  *
8  *    Redistributions of source code must retain the above copyright
9  *    notice, this list of conditions and the following disclaimer.
10  *
11  *    Redistributions in binary form must reproduce the above copyright
12  *    notice, this list of conditions and the following disclaimer in the
13  *    documentation and/or other materials provided with the
14  *    distribution.
15  *
16  *    Neither the name of Texas Instruments Incorporated nor the names of
17  *    its contributors may be used to endorse or promote products derived
18  *    from this software without specific prior written permission.
19  *
20  *  THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
21  *  "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
22  *  LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
23  *  A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
24  *  OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
25  *  SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
26  *  LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
27  *  DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
28  *  THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
29  *  (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
30  *  OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
31  *
32  *****************************************************************************/
34 #include <string.h>
35 #include "platform.h"
36 #include "types.h"
37 #include "post.h"
38 #include "net.h"
39 #include "cpmacdrv.h"
40 #include "target.h"
41 #include "qm_api.h"
42 #include "cpdma_api.h"
43 #include "pscapi.h"
45 /* CSL EMAC include */
46 #include <ti/csl/csl_cpsw.h>
47 #include <ti/csl/csl_cpsgmii.h>
48 #include <ti/csl/csl_cpsgmiiAux.h>
49 #include <ti/csl/cslr_cpsgmii.h>
50 #include <ti/csl/csl_mdio.h>
51 #include <ti/csl/csl_mdioAux.h>
53 /* BootCfg module include */
54 #include <ti/csl/csl_bootcfg.h>
55 #include <ti/csl/csl_bootcfgAux.h>
57 /* The version string */
58 #pragma DATA_SECTION(post_version, ".version")
59 #pragma DATA_ALIGN(post_version, 16)
60 char post_version[] = POST_VERSION;
62 /* OSAL functions for Platform Library */
63 uint8_t *Osal_platformMalloc (uint32_t num_bytes, uint32_t alignment)
64 {
65         return malloc(num_bytes);
66 }
68 void Osal_platformFree (uint8_t *dataPtr, uint32_t num_bytes)
69 {
70     /* Free up the memory */
71     if (dataPtr)
72     {
73         free(dataPtr);
74     }
75 }
77 /******************************************************************************
78  * Function:    post_display_led_error
79  ******************************************************************************/
80 void
81 post_display_led_error
82 (
83     POST_TEST_ID     test_id
84 )
85 {
86     uint8_t     led_status[POST_MAX_NUM_LED];
87     uint32_t    i;
89     memset(led_status, POST_LED_ON, POST_MAX_NUM_LED);
90     while (TRUE)
91     {
92         for (i = 0; i < POST_MAX_NUM_LED; i++)
93         {
94             if (post_led_status[test_id][i] == POST_LED_BLINK)
95             {
96                 if (led_status[i] == POST_LED_ON)
97                 {
98                     led_status[i] = POST_LED_OFF;
99                 }
100                 else
101                 {
102                     led_status[i] = POST_LED_ON;
103                 }
104                 platform_led(i, (PLATFORM_LED_OP)led_status[i], PLATFORM_USER_LED_CLASS);
105             }
106             else
107             {
108                 platform_led(i, (PLATFORM_LED_OP)post_led_status[test_id][i], PLATFORM_USER_LED_CLASS);
109             }
110         }
111         platform_delay(POST_LED_BLINK_DELAY);
112         /* POST in the while(1) loop to display the LED error status */
113     }
116 /******************************************************************************
117  * Function:    post_write_uart
118  ******************************************************************************/
119 Bool
120 post_write_uart
122     char*      msg
125     uint32_t i;
126     uint32_t msg_len = strlen(msg);
128     /* Write the message to the UART */
129     for (i = 0; i < msg_len; i++)
130     {
131         if (platform_uart_write(msg[i]) != Platform_EOK)
132         {
133             return FALSE;
134         }
135     }
137     return TRUE;
140 /******************************************************************************
141  * Function:    post_display_status
142  ******************************************************************************/
143 void
144 post_display_status
146     POST_TEST_ID        test_id,
147     POST_TEST_RESULT    test_result
150     uint32_t    i;
151     char        *msg;
152     char        msg1[40] = "\r\n\r\nPOST ";
153     char        msg2[] = " test passed!";
154     char        msg3[] = " test failed!";
155     char        msg4[] = " test started!";
157     msg = strcat(msg1, post_status[test_id]);
158     switch (test_id)
159     {
160     case POST_TEST_IN_PROGRESS:
161     case POST_TEST_COMPLETE:
162         /* Form the POST status message to write to the UART */
163         if (post_write_uart(msg) != TRUE)
164         {
165             post_display_led_error(POST_TEST_UART);   /* Never return from this function */
166         }
168         for (i = 0; i < POST_MAX_NUM_LED; i++)
169         {
170             if (platform_led(i, (PLATFORM_LED_OP)post_led_status[test_id][i], PLATFORM_USER_LED_CLASS) != Platform_EOK)
171             {
172                 post_write_uart("POST LED test failed \r\n");
173             }
174         }
175         break;
177     default:
178         /* Form the POST status message to write to the UART */
179         if (test_result == POST_TEST_RESULT_PASSED)
180         {
181             msg = strcat(msg, msg2);
182             if (post_write_uart(msg) != TRUE)
183             {
184                 post_display_led_error(POST_TEST_UART);   /* Never return from this function */
185             }
186         }
187         else if (test_result == POST_TEST_RESULT_FAILED)
188         {
189             msg = strcat(msg, msg3);
190             if (post_write_uart(msg) != TRUE)
191             {
192                 post_display_led_error(POST_TEST_UART);   /* Never return from this function */
193             }
194             post_display_led_error(test_id);  /* Never return from this function */
195         }
196         else
197         {
198             msg = strcat(msg, msg4);
199             if (post_write_uart(msg) != TRUE)
200             {
201                 post_display_led_error(POST_TEST_UART);   /* Never return from this function */
202             }
203         }
204         break;
205     }
208 /******************************************************************************
209  * Function:    post_test_external_memory
210  ******************************************************************************/
211 POST_TEST_RESULT
212 post_test_external_memory
214     void
217     POST_TEST_RESULT    test_result = POST_TEST_RESULT_PASSED;
219     if(platform_external_memory_test(0, 0) != Platform_EOK)
220     {
221         test_result = POST_TEST_RESULT_FAILED;
222     }
224     return test_result;
227 /******************************************************************************
228  * Function:    post_test_eeprom
229  ******************************************************************************/
230 POST_TEST_RESULT
231 post_test_eeprom
233     void
236     uint8_t                 test_buf[POST_EEPROM_TEST_READ_LENGTH];
237     POST_TEST_RESULT        test_result = POST_TEST_RESULT_PASSED;
238     PLATFORM_DEVICE_info    *p_device;
240     p_device = platform_device_open(POST_EEPROM_TEST_DEVICE_ID, 0);
241     if (p_device == NULL)
242     {
243         return POST_TEST_RESULT_FAILED;
244     }
246     if(platform_device_read(p_device->handle,
247                             POST_EEPROM_TEST_READ_ADDRESS,
248                             test_buf,
249                             POST_EEPROM_TEST_READ_LENGTH) != Platform_EOK)
250     {
251         test_result = POST_TEST_RESULT_FAILED;
252     }
254     platform_device_close(p_device->handle);
255     return test_result;
258 /******************************************************************************
259  * Function:    post_test_nand
260  ******************************************************************************/
261 POST_TEST_RESULT
262 post_test_nand
264     void
267     uint8_t                 test_buf[POST_NAND_TEST_READ_LENGTH];
268     POST_TEST_RESULT        test_result = POST_TEST_RESULT_PASSED;
269     uint32_t                addr;
270     PLATFORM_DEVICE_info    *p_device;
272     p_device = platform_device_open(POST_NAND_TEST_DEVICE_ID, 0);
273     if (p_device == NULL)
274     {
275         return POST_TEST_RESULT_FAILED;
276     }
278     addr = (POST_NAND_TEST_READ_BLOCK_NUM * p_device->page_count + POST_NAND_TEST_READ_PAGE_NUM) * p_device->page_size;
279     if(platform_device_read(p_device->handle,
280                             addr,
281                             test_buf,
282                             POST_NAND_TEST_READ_LENGTH) != Platform_EOK)
283     {
284         test_result = POST_TEST_RESULT_FAILED;
285     }
287     platform_device_close(p_device->handle);
288     return test_result;
291 /******************************************************************************
292  * Function:    post_test_nor
293  ******************************************************************************/
294 POST_TEST_RESULT
295 post_test_nor
297     void
300     uint8_t                 test_buf[POST_NOR_TEST_READ_LENGTH];
301     POST_TEST_RESULT        test_result = POST_TEST_RESULT_PASSED;
302     PLATFORM_DEVICE_info    *p_device;
304     p_device = platform_device_open(POST_NOR_TEST_DEVICE_ID, 0);
305     if (p_device == NULL)
306     {
307         return POST_TEST_RESULT_FAILED;
308     }
310     if(platform_device_read(p_device->handle,
311                             POST_NOR_TEST_READ_ADDR,
312                             test_buf,
313                             POST_NOR_TEST_READ_LENGTH) != Platform_EOK)
314     {
315         test_result = POST_TEST_RESULT_FAILED;
316     }
318     platform_device_close(p_device->handle);
319     return test_result;
322 /** Number of ports in the ethernet subsystem */
323 #define         NUM_PORTS                   3u
325 /** Number of MAC/GMII ports in the ethernet switch */
326 #define         NUM_MAC_PORTS               2u
328 /* Define LoopBack modes */
329 #define CPSW_LOOPBACK_NONE           0
330 #define CPSW_LOOPBACK_INTERNAL       1
331 #define CPSW_LOOPBACK_EXTERNAL       2
333 #ifdef  SIMULATOR_SUPPORT
334 int32_t cpswSimTest = 1;
335 int32_t cpswLpbkMode = CPSW_LOOPBACK_EXTERNAL;
336 #else
337 int32_t cpswSimTest = 0;
338 int32_t cpswLpbkMode = CPSW_LOOPBACK_INTERNAL;
339 #endif
340 int32_t cpswEvm6678 = 0;
342 /** ============================================================================
343  *   @n@b Init_SGMII
344  *
345  *   @b Description
346  *   @n SGMII peripheral initialization code.
347  *
348  *   @param[in]
349  *   @n macPortNum      MAC port number for which the SGMII port setup must
350  *                      be performed.
351  *
352  *   @return
353  *   @n None
354  * =============================================================================
355  */
356 int32_t Init_sgmii (uint32_t macPortNum)
358     CSL_SGMII_ADVABILITY    sgmiiCfg;
359         CSL_SGMII_STATUS        sgmiiStatus;
361     if ((macPortNum == 0) && (cpswEvm6678))
362     {
363         /* EVM6678 back end: MAC-to-MAC force link */
365         /* Reset the port before configuring it */
366         CSL_SGMII_doSoftReset (macPortNum);
367         while (CSL_SGMII_getSoftResetStatus (macPortNum) != 0);
369         /* Hold the port in soft reset and set up
370         * the SGMII control register:
371         *      (1) Enable Master Mode (default)
372         */
373         CSL_SGMII_startRxTxSoftReset (macPortNum);
374         CSL_SGMII_enableMasterMode (macPortNum);
375         if (cpswLpbkMode != CPSW_LOOPBACK_NONE)
376         {
377                 CSL_SGMII_enableLoopback (macPortNum);
378         }
380             /* Setup the Advertised Ability register for this port:
381         *      (1) Enable Full duplex mode
382         *      (2) Speed = 1000M
383         *      (3) Force the Link
384         */
385         sgmiiCfg.bLinkUp        =   1;
386         sgmiiCfg.linkSpeed      =   CSL_SGMII_1000_MBPS;
387         sgmiiCfg.duplexMode     =   CSL_SGMII_FULL_DUPLEX;
388         CSL_SGMII_setAdvAbility (macPortNum, &sgmiiCfg);
390         CSL_SGMII_endRxTxSoftReset (macPortNum);
392             /* Wait for SGMII Link */
393             do
394             {
395                 CSL_SGMII_getStatus(macPortNum, &sgmiiStatus);
396             } while (sgmiiStatus.bIsLinkUp != 1);
397     }
398     else
399     {
400         /* Reset the port before configuring it */
401         CSL_SGMII_doSoftReset (macPortNum);
402         while (CSL_SGMII_getSoftResetStatus (macPortNum) != 0);
404         /* Hold the port in soft reset and set up
405         * the SGMII control register:
406         *      (1) Enable Master Mode (default)
407         *      (2) Enable Auto-negotiation
408         */
409         CSL_SGMII_startRxTxSoftReset (macPortNum);
410         if (cpswLpbkMode == CPSW_LOOPBACK_NONE)
411         {
412             CSL_SGMII_disableMasterMode (macPortNum);
413         }
414         else
415         {
416             CSL_SGMII_enableMasterMode (macPortNum);
418             if (cpswLpbkMode == CPSW_LOOPBACK_INTERNAL)
419             {
420                     CSL_SGMII_enableLoopback (macPortNum);
421             }
422         }
424             /* Setup the Advertised Ability register for this port:
425         *      (1) Enable Full duplex mode
426         *      (2) Enable Auto Negotiation
427         */
428         sgmiiCfg.linkSpeed      =   CSL_SGMII_1000_MBPS;
429         sgmiiCfg.duplexMode     =   CSL_SGMII_FULL_DUPLEX;
430         CSL_SGMII_setAdvAbility (macPortNum, &sgmiiCfg);
432         CSL_SGMII_enableAutoNegotiation (macPortNum);
433         CSL_SGMII_endRxTxSoftReset (macPortNum);
435             /* Wait for SGMII Link */
436         if (!cpswSimTest && ((cpswLpbkMode == CPSW_LOOPBACK_EXTERNAL) || (cpswLpbkMode == CPSW_LOOPBACK_NONE)))
437         {
438                 do
439                 {
440                     CSL_SGMII_getStatus(macPortNum, &sgmiiStatus);
441                 } while (sgmiiStatus.bIsLinkUp != 1);
443                 /* Wait for SGMII Autonegotiation to complete without error */
444                 do
445                 {
446                     CSL_SGMII_getStatus(macPortNum, &sgmiiStatus);
447                     if (sgmiiStatus.bIsAutoNegError != 0)
448                         return -1;
449                 } while (sgmiiStatus.bIsAutoNegComplete != 1);
450         }
451     }
453     /* All done with configuration. Return Now. */
454     return 0;
457 int Init_MAC (uint32_t macPortNum, uint8_t macAddress[6], uint32_t mtu)
459     /* Reset MAC Sliver 0 */
460     CSL_CPGMAC_SL_resetMac (macPortNum);
461     while (CSL_CPGMAC_SL_isMACResetDone (macPortNum) != TRUE);
463     /* Setup the MAC Control Register for this port:
464      *      (1) Enable Full duplex
465      *      (2) Enable GMII
466      *      (3) Enable Gigabit
467      *      (4) Enable External Configuration. This enables
468      *          the "Full duplex" and "Gigabit" settings to be
469      *          controlled externally from SGMII
470      *      (5) Don't enable any control/error/short frames
471      */
472     CSL_CPGMAC_SL_enableFullDuplex (macPortNum);
473     CSL_CPGMAC_SL_enableGMII (macPortNum);
474     CSL_CPGMAC_SL_enableGigabit (macPortNum);
475     CSL_CPGMAC_SL_enableExtControl (macPortNum);
477     /* Configure the MAC address for this port */
478     CSL_CPSW_3GF_setPortMACAddress (macPortNum, macAddress);
480     /* Configure VLAN ID/CFI/Priority.
481      *
482      * For now, we are not using VLANs so just configure them
483      * to all zeros.
484      */
485     CSL_CPSW_3GF_setPortVlanReg (macPortNum, 0, 0, 0);
487     /* Configure the Receive Maximum length on this port,
488      * i.e., the maximum size the port can receive without
489      * any errors.
490      *
491      * Set the Rx Max length to the MTU configured for the
492      * interface.
493      */
494     CSL_CPGMAC_SL_setRxMaxLen (macPortNum, mtu);
496     /* Done setting up the MAC port */
497     return 0;
500 void Init_Switch (uint32_t mtu)
502     CSL_CPSW_3GF_PORTSTAT               portStatCfg;
504     /* Enable the CPPI port, i.e., port 0 that does all
505      * the data streaming in/out of EMAC.
506      */
507     CSL_CPSW_3GF_enablePort0 ();
508     CSL_CPSW_3GF_disableVlanAware ();
509     CSL_CPSW_3GF_setPort0VlanReg (0, 0, 0);
510     CSL_CPSW_3GF_setPort0RxMaxLen (mtu);
512     /* Enable statistics on both the port groups:
513      *
514      * MAC Sliver ports -   Port 1, Port 2
515      * CPPI Port        -   Port 0
516      */
517     portStatCfg.p0AStatEnable   =   1;
518     portStatCfg.p0BStatEnable   =   1;
519     portStatCfg.p1StatEnable    =   1;
520     portStatCfg.p2StatEnable    =   1;
521     CSL_CPSW_3GF_setPortStatsEnableReg (&portStatCfg);
523     /* Setup the Address Lookup Engine (ALE) Configuration:
524      *      (1) Enable ALE.
525      *      (2) Clear stale ALE entries.
526      *      (3) Disable VLAN Aware lookups in ALE since
527      *          we are not using VLANs by default.
528      *      (4) No Flow control
529      *      (5) Configure the Unknown VLAN processing
530      *          properties for the switch, i.e., which
531      *          ports to send the packets to.
532      */
533     CSL_CPSW_3GF_enableAle ();
534     CSL_CPSW_3GF_clearAleTable ();
536     CSL_CPSW_3GF_disableAleVlanAware ();
537     CSL_CPSW_3GF_disableAleTxRateLimit ();
538     CSL_CPSW_3GF_setAlePrescaleReg (125000000u/1000u);
539     CSL_CPSW_3GF_setAleUnkownVlanReg (7, 3, 3, 7);
541     if(cpswLpbkMode != CPSW_LOOPBACK_NONE)
542         CSL_CPSW_3GF_enableAleBypass();
544     /* Done with switch configuration */
545     return;
548 int Switch_update_addr (uint32_t portNum, uint8_t macAddress[6], Uint16 add)
550     uint32_t                              i;
551     CSL_CPSW_3GF_ALE_PORTCONTROL        alePortControlCfg;
552     CSL_CPSW_3GF_ALE_UNICASTADDR_ENTRY  ucastAddrCfg;
555     /* Configure the address in "Learning"/"Forward" state */
556     alePortControlCfg.portState             =   ALE_PORTSTATE_FORWARD;
557     alePortControlCfg.dropUntaggedEnable    =   0;
558     alePortControlCfg.vidIngressCheckEnable =   0;
559     alePortControlCfg.noLearnModeEnable     =   (cpswLpbkMode != CPSW_LOOPBACK_NONE)?1:0;
560     alePortControlCfg.mcastLimit            =   0;
561     alePortControlCfg.bcastLimit            =   0;
563     CSL_CPSW_3GF_setAlePortControlReg (portNum, &alePortControlCfg);
565     if (cpswLpbkMode != CPSW_LOOPBACK_NONE)
566     {
567         /* Program the ALE with the MAC address.
568         *
569         * The ALE entries determine the switch port to which any
570         * matching received packet must be forwarded to.
571         */
572         /* Get the next free ALE entry to program */
573         for (i = 0; i < CSL_CPSW_3GF_NUMALE_ENTRIES; i++)
574         {
575             if (CSL_CPSW_3GF_getALEEntryType (i) == ALE_ENTRYTYPE_FREE)
576             {
577                 /* Found a free entry */
578                 break;
579             }
580         }
581         if (i == CSL_CPSW_3GF_NUMALE_ENTRIES)
582         {
583             /* No free ALE entry found. return error. */
584             return -1;
585         }
586         else
587         {
588             /* Found a free ALE entry to program our MAC address */
589             memcpy (ucastAddrCfg.macAddress, macAddress, 6);    // Set the MAC address
590             ucastAddrCfg.ucastType      =      ALE_UCASTTYPE_UCAST_NOAGE;   // Add a permanent unicast address entryALE_UCASTTYPE_UCAST_NOAGE.
591             ucastAddrCfg.secureEnable   =      FALSE;
592             ucastAddrCfg.blockEnable    =      FALSE;
593             ucastAddrCfg.portNumber     =      portNum;   // Add the ALE entry for this port
595             /* Setup the ALE entry for this port's MAC address */
596             CSL_CPSW_3GF_setAleUnicastAddrEntry (i, &ucastAddrCfg);
597         }
598     }
600     /* Done with upading address */
601     return 0;
604 int32_t Init_SGMII_SERDES(void)
606     if (cpswSimTest)
607     {
609             /* Unlock the chip configuration registers to allow SGMII SERDES registers to
610             * be written */
611             CSL_BootCfgUnlockKicker();
613         CSL_BootCfgSetSGMIIConfigPLL (0x00000041);
614         CSL_BootCfgSetSGMIIRxConfig (0, 0x00700621);
615         CSL_BootCfgSetSGMIITxConfig (0, 0x000108A1);
616         CSL_BootCfgSetSGMIIRxConfig (1, 0x00700621);
617         CSL_BootCfgSetSGMIITxConfig (1, 0x000108A1);
619             /* Re-lock the chip configuration registers to prevent unintentional writes */
620             CSL_BootCfgLockKicker();
622     }
624         /* SGMII SERDES Configuration complete. Return. */
625         return 0;
628 int32_t Init_Cpsw (void)
630     uint32_t       macPortNum, mtu = 1518;
631     uint8_t        mac_address[6];
632     uint8_t        sw_port0_mac_addr[6] = {0x10, 0x11, 0x12, 0x13, 0x14, 0x15};
634         /* Initialize the SERDES modules */
635         Init_SGMII_SERDES();
637     platform_get_macaddr(PLATFORM_MAC_TYPE_EFUSE, mac_address);
639     /* Initialize the SGMII/Sliver submodules for the
640      * two corresponding MAC ports.
641      */
642     for (macPortNum = 0; macPortNum < NUM_MAC_PORTS; macPortNum++)
643     {
644         if (Init_sgmii (macPortNum))
645                   return -1;
646         mac_address[5] += macPortNum;
647         Init_MAC (macPortNum, mac_address, mtu);
648         mac_address[5] -= macPortNum;
649     }
651     /* Setup the Ethernet switch finally. */
652     Init_Switch (mtu);
654     Switch_update_addr(0, sw_port0_mac_addr, 0);
655     Switch_update_addr(1, mac_address, 0);
656     mac_address[5] += 1;
657     Switch_update_addr(2, mac_address, 0);
659     /* CPSW subsystem setup done. Return success */
660     return 0;
664 /******************************************************************************
665  * Function:    post_test_emac_loopback
666  ******************************************************************************/
667 POST_TEST_RESULT
668 post_test_emac_loopback
670     void
673     uint8_t   test_buf[POST_EMAC_TEST_PKT_LENGTH+14];
674     uint8_t   sw_port0_mac_addr[6] = {0x10, 0x11, 0x12, 0x13, 0x14, 0x15};
675     uint8_t   mac_address[6];
676     NET_DRV_DEVICE nDevice;
677     uint32_t modNum;
678     int32_t  ret;
680     /* Note that if the sgmii power enable is requested the PA must be
681      * powered up first */
682     modNum = 8;
683     if (modNum == TARGET_PWR_ETH(x))  {
684         ret = (int32_t)pscEnableModule (TARGET_PWR_PA);
685         if (ret != 0)
686             return (POST_TEST_RESULT_FAILED);
687     }
689     ret = (int32_t)pscEnableModule(modNum);
690     if (ret != 0)
691         return (POST_TEST_RESULT_FAILED);
693     Init_Cpsw();
695     /* Queue manager configuration */
696     hwQmSetup ((qmConfig_t *)(targetGetQmConfig()));
697     targetInitQs ();
700     /* Cpdma configuration. */
701     hwCpdmaRxConfig ((cpdmaRxCfg_t *)targetGetCpdmaRxConfig());
702     hwCpdmaTxConfig ((cpdmaTxCfg_t *)targetGetCpdmaTxConfig());
705     /* Packet accelerator configuration. If PA is not present this statement is defined
706      * to void in target.h */
707     targetPaConfig(sw_port0_mac_addr);
709     /* Streaming switch configuration. If not present this statement is defined to void
710      * in target.h.  If present this is usually defined to a series of register writes */
711     hwConfigStreamingSwitch();
713     /* Initialize the network device driver */
714     memset (&nDevice, 0, sizeof(nDevice));
716     /* Start the networking device */
717     if (cpmac_drv_start(&nDevice) < 0)
718     {
719         return POST_TEST_RESULT_FAILED;
720     }
722     /* Get the MAC address from efuse */
723     platform_get_macaddr(PLATFORM_MAC_TYPE_EFUSE, mac_address);
725     /* Set the dest MAC address to be broadcast, so that PA firmware will not filter out */
726     memset(test_buf, 0xff, 6);
727     memcpy(&test_buf[6], sw_port0_mac_addr, 6);
729     /* set the payload length to 256 bytes */
730     test_buf[12] = 0x01;
731     test_buf[13] = 0x00;
733     /* Send the Ethernet packet */
734     if (cpmac_drv_send (&nDevice, test_buf, POST_EMAC_TEST_PKT_LENGTH+14) < 0)
735     {
736         return POST_TEST_RESULT_FAILED;
737     }
738     
739     platform_delay(100);
740     
741     /* Receive the loopback packet */
742     if (ret = cpmac_drv_receive (&nDevice, test_buf) < 0)
743     {
744         return POST_TEST_RESULT_FAILED;
745     }
747     return POST_TEST_RESULT_PASSED;
750 void
751 post_hex_to_string
753     uint32_t    hex,
754     uint32_t    nibbles,
755     char        *msg
758     int32_t     i;
759     uint8_t     nibble;
761     for (i = (nibbles-1); i >= 0; i--)
762     {
763         nibble = hex & 0xf;
764         if (nibble <= 0x9)
765         {
766             nibble += '0';
767         }
768         else
769         {
770             nibble += ('A' - 0xa);
771         }
773         msg[i] = nibble;
774         hex = hex >> 4;
775     }
776     msg[nibbles] = 0;
779 Bool
780 post_serial_num_isvalid
782     char    c
785     if (
786         ((c >= '0') && (c <= '9'))    ||
787         ((c >= 'a') && (c <= 'z'))    ||
788         ((c >= 'A') && (c <= 'Z'))
789        )
790     {
791         return TRUE;
792     }
793     else
794     {
795         return FALSE;
796     }
799 /******************************************************************************
800  * Function:    post_write_serial_no
801  ******************************************************************************/
802 void
803 post_write_serial_no
805     void
808     uint32_t                i, j;
809     uint8_t                 msg[20], msg2[2];
810     PLATFORM_DEVICE_info    *p_device;
812     /* Check if user key in the passcode "ti" to enter board serial number */
813     if (platform_uart_read(msg, POST_UART_READ_TIMEOUT) != Platform_EOK)
814     {
815         return;
816     }
817     if (msg[0] != 't')
818     {
819         return;
820     }
822     if (platform_uart_read(msg, POST_UART_READ_TIMEOUT) != Platform_EOK)
823     {
824         return;
825     }
826     if (msg[0] != 'i')
827     {
828         return;
829     }
831     /* Passcode verified, prompt the user to enter serial number */
832     p_device = platform_device_open(PLATFORM_DEVID_EEPROM50, 0);
833     if (p_device == NULL)
834     {
835         return;
836     }
838     post_write_uart("\r\n\r\nPlease enter the 10 digit serial number for this board, and then press ENTER key:\r\n\r\n");
840     i = 0;
841     msg2[1] = 0;
842     while (TRUE)
843     {
844         if (platform_uart_read(&msg[i], POST_UART_READ_TIMEOUT) != Platform_EOK)
845         {
846             platform_device_close(p_device->handle);
847             post_write_uart("\r\n\r\nSerial number input time out!");
848             return;
849         }
851         if (msg[i] == '\r')
852         {
853             break;
854         }
855         if ((i < POST_MAX_SN_SIZE) &&  post_serial_num_isvalid(msg[i]))
856         {
857             msg2[0] = msg[i];
858             post_write_uart((char *)msg2);
859             i++;
860         }
861     }
863     if (i < POST_MAX_SN_SIZE)
864     {
865         for (j = i; j < POST_MAX_SN_SIZE; j++)
866         {
867             msg[j] = 0xff;
868         }
869     }
871     if(platform_device_write(p_device->handle, POST_SERIAL_NUM_ADDR, msg, 16) == Platform_EOK)
872     {
873         post_write_uart("\r\n\r\nSerial number programmed to EEPROM successfully! ");
874     }
875     else
876     {
877         post_write_uart("\r\n\r\nFailed to program the serial number to EEPROM!");
878     }
879     platform_device_close(p_device->handle);
883 /******************************************************************************
884  * Function:    main function for POST
885  ******************************************************************************/
886 void
887 main
889     void
892     platform_init_flags     init_flags;
893     platform_init_config    init_config;
894     POST_TEST_ID            test_id = POST_TEST_IN_PROGRESS;
895     POST_TEST_RESULT        test_result;
896     uint32_t                reset_type;
897     int32_t                 i;
898     char                    msg[9];
899     uint8_t                 mac_addr[6];
900     platform_info           info;
901     uint32_t                sa_enable;
903     /* Turn on all the platform initialize flags */
904     memset(&init_config, 0, sizeof(platform_init_config));
905     memset(&init_flags, 0x01, sizeof(platform_init_flags));
907     init_flags.phy = 0;
909     /* Initialize the platform */
910     if (platform_init(&init_flags, &init_config) != Platform_EOK)
911     {
912         switch (platform_errno)
913         {
914         case PLATFORM_ERRNO_PLL_SETUP:
915             test_id = POST_TEST_PLL_INIT;
916             break;
917         case PLATFORM_ERRNO_NAND:
918             test_id = POST_TEST_NAND_INIT;
919             break;
920         case PLATFORM_ERRNO_NOR:
921             test_id = POST_TEST_NOR_INIT;
922             break;
923         default:
924             test_id = POST_TEST_GENERAL;
925             break;
926         }
927         test_result = POST_TEST_RESULT_FAILED;
928     }
930     platform_uart_init();
931     platform_uart_set_baudrate(POST_UART_BAUDRATE);
932     if (test_id != POST_TEST_PLL_INIT)
933     {
934         if (post_write_uart("\r\n\r\n") != TRUE)
935         {
936             post_display_led_error(POST_TEST_UART);   /* Never return from this function */
937         }
939         platform_get_info(&info);
941         /* Display the board name */
942         post_write_uart(info.board_name);
944         /* Display the POST version */
945         post_write_uart(POST_EVM_VERSION_MSG);
946         post_write_uart(post_version);
948         post_hex_to_string(info.board_rev, 4, msg);
949         post_write_uart("\r\n\r\nFPGA Version: ");
950         post_write_uart(msg);
952         if (info.serial_nbr[0] != 0)
953         {
954             post_write_uart("\r\n\r\nBoard Serial Number: ");
955             post_write_uart(info.serial_nbr);
956         }
958         /* Display the EFUSE MAC address */
959         platform_get_macaddr(PLATFORM_MAC_TYPE_EFUSE, mac_addr);
960         post_write_uart("\r\n\r\nEFUSE MAC ID is: ");
961         for (i = 0; i < 6; i++)
962         {
963             post_hex_to_string(info.emac.efuse_mac_address[i], 2, msg);
964             msg[2] = ' ';
965             msg[3] = 0;
966             post_write_uart(msg);
967         }
969         sa_enable = *(volatile uint32_t *)0x20c0004;
970         sa_enable &= 0x1;
972         if (sa_enable)
973         {
974             post_write_uart("\r\n\r\nSA is enabled on this board.");
975         }
976         else
977         {
978             post_write_uart("\r\n\r\nSA is disabled on this board.");
979         }
981         /* Read the PLL Reset Type Status register and display on UART */
982         reset_type = PLL_CTRL_REG_RSTYPE;
983         post_hex_to_string(reset_type, 8, msg);
984         post_write_uart("\r\n\r\nPLL Reset Type Status Register: 0x");
985         post_write_uart(msg);
986     }
988     /* Display test in progress UART/LED status or init error */
989     post_display_status(test_id, POST_TEST_RESULT_STARTED);
991     post_display_status(POST_TEST_EEPROM, POST_TEST_RESULT_STARTED);
992     test_result = post_test_eeprom();
993     post_display_status(POST_TEST_EEPROM, test_result);
995     post_display_status(POST_TEST_NOR, POST_TEST_RESULT_STARTED);
996     test_result = post_test_nor();
997     post_display_status(POST_TEST_NOR, test_result);
999     post_display_status(POST_TEST_NAND, POST_TEST_RESULT_STARTED);
1000     test_result = post_test_nand();
1001     post_display_status(POST_TEST_NAND, test_result);
1003     post_display_status(POST_TEST_EMAC_LOOPBACK, POST_TEST_RESULT_STARTED);
1004     test_result = post_test_emac_loopback();
1005     post_display_status(POST_TEST_EMAC_LOOPBACK, test_result);
1007     post_display_status(POST_TEST_DDR, POST_TEST_RESULT_STARTED);
1008     test_result = post_test_external_memory();
1009     post_display_status(POST_TEST_DDR, test_result);
1011     post_display_status(POST_TEST_COMPLETE, POST_TEST_RESULT_PASSED);
1013     post_write_serial_no();