/** * \brief EMAC link test function. * * \param test Current test case. */ static void run_emac_link_test(const struct test_case *test) { volatile uint32_t ul_delay; emac_options_t emac_option; uint8_t uc_rc = 1; /* Reset PHY */ rstc_set_external_reset(RSTC, 13); /* (2^(13+1))/32768 */ rstc_reset_extern(RSTC); while (rstc_get_status(RSTC) & RSTC_SR_NRSTL) { }; rstc_set_external_reset(RSTC, 0); /* restore default */ /* Wait for PHY to be ready (CAT811: Max400ms) */ ul_delay = sysclk_get_cpu_hz() / 1000 / 3 * 400; while (ul_delay--); /* Enable EMAC clock */ pmc_enable_periph_clk(ID_EMAC); /* Fill in EMAC options */ emac_option.uc_copy_all_frame = 1; emac_option.uc_no_boardcast = 1; memcpy(emac_option.uc_mac_addr, gs_uc_mac_address, sizeof(gs_uc_mac_address)); gs_emac_dev.p_hw = EMAC; /* Init EMAC driver structure */ emac_dev_init(EMAC, &gs_emac_dev, &emac_option); /* Enable Interrupt */ NVIC_EnableIRQ(EMAC_IRQn); /* Init MAC PHY driver */ if (ethernet_phy_init(EMAC, BOARD_EMAC_PHY_ADDR, sysclk_get_cpu_hz()) != EMAC_OK) { uc_rc = 0; } /* Auto Negotiate, work in RMII mode */ if (ethernet_phy_auto_negotiate(EMAC, BOARD_EMAC_PHY_ADDR) != EMAC_OK) { uc_rc = 0; } /* Establish ethernet link */ while (ethernet_phy_set_link(EMAC, BOARD_EMAC_PHY_ADDR, 1) != EMAC_OK) { uc_rc = 0; } test_assert_true(test, uc_rc == 1, "Test EMAC: EMAC link test error!"); }
void ethernet_hardware_init(void) { /* Reset PHY */ //rstc_set_external_reset(RSTC, 13); /* (2^(13+1))/32768 */ // rstc_set_external_reset(RSTC, 15); // rstc_reset_extern(RSTC); // while (rstc_get_status(RSTC) & RSTC_SR_NRSTL) { // } // ResetEther(); while(ResettingEther()) {} /* Wait for PHY to be ready (CAT811: Max400ms) */ { volatile u32_t ul_dealy = SystemCoreClock / 6; while (ul_dealy--) { } } /* Enable EMAC clock */ pmc_enable_periph_clk(ID_EMAC); { emac_options_t emac_option; /* Fill in EMAC options */ emac_option.uc_copy_all_frame = 1; emac_option.uc_no_boardcast = 0; memcpy(emac_option.uc_mac_addr, gs_uc_mac_address, sizeof(gs_uc_mac_address)); gs_emac_dev.p_hw = EMAC; /* Init EMAC driver structure */ emac_dev_init(EMAC, &gs_emac_dev, &emac_option); } /* Enable Interrupt */ NVIC_EnableIRQ(EMAC_IRQn); /* Init MAC PHY driver */ if (ethernet_phy_init(EMAC, BOARD_EMAC_PHY_ADDR, SystemCoreClock) != EMAC_OK) { LWIP_DEBUGF(LWIP_DBG_TRACE, ("PHY Initialize ERROR!\r")); return; } }
/** * \brief In this function, the hardware should be initialized. * Called from ethernetif_init(). * * \param netif the already initialized lwip network interface structure * for this ethernetif */ static void low_level_init(struct netif *netif) { volatile uint32_t ul_dealy; emac_options_t emac_option; #ifdef FREERTOS_USED unsigned portBASE_TYPE uxPriority; #endif /* Set MAC hardware address length */ netif->hwaddr_len = sizeof(gs_uc_mac_address); /* Set MAC hardware address */ netif->hwaddr[0] = gs_uc_mac_address[0]; netif->hwaddr[1] = gs_uc_mac_address[1]; netif->hwaddr[2] = gs_uc_mac_address[2]; netif->hwaddr[3] = gs_uc_mac_address[3]; netif->hwaddr[4] = gs_uc_mac_address[4]; netif->hwaddr[5] = gs_uc_mac_address[5]; /* Maximum transfer unit */ netif->mtu = NET_MTU; /* Configure EMAC pins */ gpio_configure_pin(PIN_EEMAC_EREFCK, PIN_EMAC_FLAGS); gpio_configure_pin(PIN_EMAC_ETX0, PIN_EMAC_FLAGS); gpio_configure_pin(PIN_EMAC_ETX1, PIN_EMAC_FLAGS); gpio_configure_pin(PIN_EMAC_ETXEN, PIN_EMAC_FLAGS); gpio_configure_pin(PIN_EMAC_ECRSDV, PIN_EMAC_FLAGS); gpio_configure_pin(PIN_EMAC_ERX0, PIN_EMAC_FLAGS); gpio_configure_pin(PIN_EMAC_ERX1, PIN_EMAC_FLAGS); gpio_configure_pin(PIN_EMAC_ERXER, PIN_EMAC_FLAGS); gpio_configure_pin(PIN_EMAC_EMDC, PIN_EMAC_FLAGS); gpio_configure_pin(PIN_EMAC_EMDIO, PIN_EMAC_FLAGS); /* device capabilities */ /* don't set NETIF_FLAG_ETHARP if this device is not an ethernet one */ netif->flags |= NETIF_FLAG_BROADCAST | NETIF_FLAG_ETHARP #if defined(DHCP_USED) | NETIF_FLAG_DHCP #endif ; #ifdef FREERTOS_USED /* * NOTE: This routine contains code that polls status bits. If the Ethernet * cable is not plugged in then this can take a considerable time. To prevent * this from starving lower priority tasks of processing time we lower our * priority prior to the call, then raise it back again once the initialization * is complete. */ /* Read the priority of the current task. */ uxPriority = uxTaskPriorityGet( NULL ); /* Set the priority of the current task to the lowest possible. */ vTaskPrioritySet( NULL, tskIDLE_PRIORITY ); #endif /* Reset PHY */ rstc_set_external_reset(RSTC, 13); /* (2^(13+1))/32768 */ rstc_reset_extern(RSTC); while (rstc_get_status(RSTC) & RSTC_SR_NRSTL) { } /* Wait for PHY to be ready (CAT811: Max400ms) */ ul_dealy = sysclk_get_cpu_hz() / 6; while (ul_dealy--) { } /* Enable EMAC clock */ pmc_enable_periph_clk(ID_EMAC); /* Fill in EMAC options */ emac_option.uc_copy_all_frame = 0; emac_option.uc_no_boardcast = 0; memcpy(emac_option.uc_mac_addr, gs_uc_mac_address, sizeof(gs_uc_mac_address)); gs_emac_dev.p_hw = EMAC; /* Init EMAC driver structure */ emac_dev_init(EMAC, &gs_emac_dev, &emac_option); /* Enable Interrupt */ NVIC_EnableIRQ(EMAC_IRQn); /* Init MAC PHY driver */ if (ethernet_phy_init(EMAC, BOARD_EMAC_PHY_ADDR, sysclk_get_cpu_hz()) != EMAC_OK) { LWIP_DEBUGF(LWIP_DBG_TRACE, "PHY Initialize ERROR!\r"); return; } /* Auto Negotiate, work in RMII mode */ if (ethernet_phy_auto_negotiate(EMAC, BOARD_EMAC_PHY_ADDR) != EMAC_OK) { LWIP_DEBUGF(LWIP_DBG_TRACE, "Auto Negotiate ERROR!\r"); return; } /* Establish ethernet link */ while (ethernet_phy_set_link(EMAC, BOARD_EMAC_PHY_ADDR, 1) != EMAC_OK) { LWIP_DEBUGF(LWIP_DBG_TRACE, "Set link ERROR!\r"); } #ifdef FREERTOS_USED /* Restore the priority of the current task. */ vTaskPrioritySet( NULL, uxPriority ); /* Create the task that handles the EMAC input packets. */ sys_thread_new( "ETHINT", ethernetif_input, netif, netifINTERFACE_TASK_STACK_SIZE, netifINTERFACE_TASK_PRIORITY ); #endif }