error_t ipv4Init(NetInterface *interface) { //Identification field is primarily used to identify //fragments of an original IP datagram interface->ipv4Identification = 0; //Create a mutex to prevent simultaneous access to the IPv4 filter table interface->ipv4FilterMutex = osMutexCreate(FALSE); //Any error to report? if(interface->ipv4FilterMutex == OS_INVALID_HANDLE) return ERROR_OUT_OF_RESOURCES; //Clear IPv4 filter table contents memset(interface->ipv4Filter, 0, sizeof(interface->ipv4Filter)); //No entry in the filter table interface->ipv4FilterSize = 0; #if (IPV4_FRAG_SUPPORT == ENABLED) //Create a mutex to prevent simultaneous access to the reassembly queue interface->ipv4FragQueueMutex = osMutexCreate(FALSE); //Any error to report? if(interface->ipv4FragQueueMutex == OS_INVALID_HANDLE) { //Clean up side effects osMutexClose(interface->ipv4FilterMutex); //Stop immediately return ERROR_OUT_OF_RESOURCES; } //Clear the reassembly queue memset(interface->ipv4FragQueue, 0, sizeof(interface->ipv4FragQueue)); #endif //Successful initialization return NO_ERROR; }
error_t tcpIpStackConfigInterface(NetInterface *interface) { error_t error; //IPv6 specific variables #if (IPV6_SUPPORT == ENABLED) Ipv6Addr solicitedNodeAddr; #endif //Disable Ethernet controller interrupts interface->nicDriver->disableIrq(interface); //Start of exception handling block do { //Receive notifications when the transmitter is ready to send interface->nicTxEvent = osEventCreate(FALSE, FALSE); //Out of resources? if(interface->nicTxEvent == OS_INVALID_HANDLE) { //Report an error error = ERROR_OUT_OF_RESOURCES; //Stop immediately break; } //Receive notifications when a Ethernet frame has been received, //or the link status has changed interface->nicRxEvent = osEventCreate(FALSE, FALSE); //Out of resources? if(interface->nicRxEvent == OS_INVALID_HANDLE) { //Report an error error = ERROR_OUT_OF_RESOURCES; //Stop immediately break; } //Create a mutex to prevent simultaneous access to the NIC driver interface->nicDriverMutex = osMutexCreate(FALSE); //Out of resources? if(interface->nicDriverMutex == OS_INVALID_HANDLE) { //Report an error error = ERROR_OUT_OF_RESOURCES; //Stop immediately break; } //Ethernet controller configuration error = interface->nicDriver->init(interface); //Any error to report? if(error) break; //Ethernet related initialization error = ethInit(interface); //Any error to report? if(error) break; //IPv4 specific initialization #if (IPV4_SUPPORT == ENABLED) //Network layer initialization error = ipv4Init(interface); //Any error to report? if(error) break; //ARP cache initialization error = arpInit(interface); //Any error to report? if(error) break; #if (IGMP_SUPPORT == ENABLED) //IGMP related initialization error = igmpInit(interface); //Any error to report? if(error) break; //Join the all-systems group error = ipv4JoinMulticastGroup(interface, IGMP_ALL_SYSTEMS_ADDR); //Any error to report? if(error) break; #endif #endif //IPv6 specific initialization #if (IPV6_SUPPORT == ENABLED) //Network layer initialization error = ipv6Init(interface); //Any error to report? if(error) break; //Neighbor cache initialization error = ndpInit(interface); //Any error to report? if(error) break; #if (MLD_SUPPORT == ENABLED) ///MLD related initialization error = mldInit(interface); //Any error to report? if(error) break; #endif //Join the All-Nodes multicast address error = ipv6JoinMulticastGroup(interface, &IPV6_LINK_LOCAL_ALL_NODES_ADDR); //Any error to report? if(error) break; //Form the Solicited-Node address for the link-local address error = ipv6ComputeSolicitedNodeAddr(&interface->ipv6Config.linkLocalAddr, &solicitedNodeAddr); //Any error to report? if(error) break; //Join the Solicited-Node multicast group for each assigned address error = ipv6JoinMulticastGroup(interface, &solicitedNodeAddr); //Any error to report? if(error) break; #endif //Create a task to process incoming frames interface->rxTask = osTaskCreate("TCP/IP Stack (RX)", tcpIpStackRxTask, interface, TCP_IP_RX_STACK_SIZE, TCP_IP_RX_PRIORITY); //Unable to create the task? if(interface->rxTask == OS_INVALID_HANDLE) error = ERROR_OUT_OF_RESOURCES; //End of exception handling block } while(0); //Check whether the interface is fully configured if(!error) { //Successful interface configuration interface->configured = TRUE; //Interrupts can be safely enabled interface->nicDriver->enableIrq(interface); } else { //Clean up side effects before returning osEventClose(interface->nicTxEvent); osEventClose(interface->nicRxEvent); osMutexClose(interface->nicDriverMutex); } //Return status code return error; }
error_t icecastClientStart(IcecastClientContext *context, const IcecastClientSettings *settings) { error_t error; OsTask *task; //Debug message TRACE_INFO("Starting Icecast client...\r\n"); //Ensure the parameters are valid if(!context || !settings) return ERROR_INVALID_PARAMETER; //Clear the Icecast client context memset(context, 0, sizeof(IcecastClientContext)); //Save user settings context->settings = *settings; //Get the size of the circular buffer context->bufferSize = settings->bufferSize; //Start of exception handling block do { //Allocate a memory block to hold the circular buffer context->streamBuffer = osMemAlloc(context->bufferSize); //Failed to allocate memory? if(!context->streamBuffer) { //Report an error to the calling function error = ERROR_OUT_OF_MEMORY; break; } //Create mutex object to protect critical sections context->mutex = osMutexCreate(FALSE); //Failed to create mutex object? if(context->mutex == OS_INVALID_HANDLE) { //Report an error to the calling function error = ERROR_OUT_OF_RESOURCES; break; } //Create events to get notified when the buffer is writable/readable context->writeEvent = osEventCreate(FALSE, TRUE); context->readEvent = osEventCreate(FALSE, FALSE); //Failed to create event object? if(context->writeEvent == OS_INVALID_HANDLE || context->readEvent == OS_INVALID_HANDLE) { //Report an error to the calling function error = ERROR_OUT_OF_RESOURCES; break; } //Create the Icecast client task task = osTaskCreate("Icecast client", icecastClientTask, context, ICECAST_CLIENT_STACK_SIZE, ICECAST_CLIENT_PRIORITY); //Unable to create the task? if(task == OS_INVALID_HANDLE) { //Report an error to the calling function error = ERROR_OUT_OF_RESOURCES; break; } //Successful initialization error = NO_ERROR; //End of exception handling block } while(0); //Check whether an error occurred if(error) { //Clean up side effects... osMemFree(context->streamBuffer); osMutexClose(context->mutex); osEventClose(context->writeEvent); osEventClose(context->readEvent); } //Return status code return error; }