static void rza1_recv_task(void *arg) { struct netif *netif = (struct netif*)arg; u16_t recv_size; struct pbuf *p; int cnt; while (1) { sys_arch_sem_wait(&recv_ready_sem, 0); for (cnt = 0; cnt < 16; cnt++) { recv_size = ethernet_receive(); if (recv_size != 0) { p = pbuf_alloc(PBUF_RAW, recv_size, PBUF_RAM); if (p != NULL) { (void)ethernet_read((char *)p->payload, p->len); /* full packet send to tcpip_thread to process */ if (netif->input(p, netif) != ERR_OK) { /* Free buffer */ pbuf_free(p); } } } else { break; } } } }
static void emac_read_packet(uint32_t ul_status) { // Because the LWIP stack can become corrupted if we work with it in parallel, // we may have to wait for the next Spin() call to read the next packet. if (LockLWIP()) { do { // read all queued packets from the RX buffer } while (ethernet_read()); UnlockLWIP(); } else { reprap.GetNetwork()->ReadPacket(); ethernet_set_rx_callback(NULL); } }
static void rza1_recv_task(void *arg) { struct netif *netif = (struct netif*)arg; struct eth_hdr *ethhdr; u16_t recv_size; struct pbuf *p; int cnt; while (1) { sys_arch_sem_wait(&recv_ready_sem, 0); for (cnt = 0; cnt < 16; cnt++) { recv_size = ethernet_receive(); if (recv_size != 0) { p = pbuf_alloc(PBUF_RAW, recv_size, PBUF_RAM); if (p != NULL) { (void)ethernet_read((char *)p->payload, p->len); ethhdr = p->payload; switch (htons(ethhdr->type)) { case ETHTYPE_IP: case ETHTYPE_ARP: #if PPPOE_SUPPORT case ETHTYPE_PPPOEDISC: case ETHTYPE_PPPOE: #endif /* PPPOE_SUPPORT */ /* full packet send to tcpip_thread to process */ if (netif->input(p, netif) != ERR_OK) { /* Free buffer */ pbuf_free(p); } break; default: /* Return buffer */ pbuf_free(p); break; } } } else { break; } } } }
void Network::Spin() { // Basically we can't do anything if we can't interact with LWIP if (!LockLWIP()) { platform->ClassReport(longWait); return; } if (state == NetworkActive) { // See if we can read any packets if (readingData) { readingData = false; do { // read all queued packets from the RX buffer } while (ethernet_read()); ethernet_set_rx_callback(&emac_read_packet); } // See if we can send anything NetworkTransaction *r = writingTransactions; if (r != NULL && r->Send()) { // We're done, free up this transaction ConnectionState *cs = r->cs; NetworkTransaction *rn = r->nextWrite; writingTransactions = r->next; AppendTransaction(&freeTransactions, r); // If there is more data to write on this connection, do it next time if (cs != NULL) { cs->sendingTransaction = rn; } if (rn != NULL) { PrependTransaction(&writingTransactions, rn); } } } else if (state == NetworkInitializing && establish_ethernet_link()) { start_ethernet(platform->IPAddress(), platform->NetMask(), platform->GateWay()); ethernet_set_rx_callback(&emac_read_packet); httpd_init(); ftpd_init(); telnetd_init(); netbios_init(); state = NetworkActive; } UnlockLWIP(); platform->ClassReport(longWait); }