//process incoming packet public static bool ProcessIncomingPacket(Bytes packet, IpHeader ipHeader) { int offset = EthernetHeader.Size + IpHeader.Size; //14 byte ethernet header + 20 byte IP header VTable.Assert(offset == 34); UDPHeader udpHeader = new UDPHeader(packet, offset); DebugPrint("ProcessIncomingPacket: Received packet from address {0} port {1}\n", ipHeader.srcAddress.ToString(), udpHeader.srcPort); UDP udp = GetUDPSession(udpHeader.dstPort); //now we check to see whether the udp session wants to packet //XXX review this logic... //todo: check if udp is bound to local IP that dest IP matches. //UDP header? if ((udp != null) && ((udp.LocalAddress == IPv4.Any) || (udp.RemoteAddress == ipHeader.srcAddress && udp.RemotePort == udpHeader.srcPort) || (udp.RemotePort == 0))) { offset += UDPHeader.Size; Bytes data = Bitter.SplitOff(ref packet, offset); //delete packet; udp.PushPacket(data); udp.udpWaitEvent.Set(); return(true); } DebugPrint("Received packe destined for inactive UDP port {0}" + " source address {1} source port {2}\n", udpHeader.dstPort, ipHeader.srcAddress.ToString(), udpHeader.srcPort); //delete packet; return(false); }
//assume ethernet //we have to expose this for the DhcpClient //Once we move the Dhcp client into an app this can be hidden again public void WriteCompleteUDPHeader(Bytes header, Bytes data, int payloadLength) { int totalLength = IpHeader.Size + UDPHeader.Size + payloadLength; //write ip header int offset = EthernetHeader.Size; int o = EthernetHeader.Size; DebugStub.Assert(payloadLength < 0xffff); header[o++] = 0x45; //default version 4, header_len 5 header[o++] = 0; //tos header[o++] = (byte)(((ushort)totalLength) >> 8); //total length of the ip header header[o++] = (byte)(((ushort)totalLength) & 0xff); header[o++] = (byte)(((ushort)0) >> 8); //fragment id header[o++] = (byte)(((ushort)0) & 0xff); //fragment id header[o++] = (byte)(((ushort)0) >> 8); //fragment offset header[o++] = (byte)(((ushort)0) & 0xff); //fragment offset header[o++] = 128; //default ttl header[o++] = 17; // protocol ID --> udp header[o++] = 0; //ipchecksum (fill it in later) header[o++] = 0; //ipchecksum // set the ip addresses localIPAddress.CopyOut(header.Array, header.Start + o); o += IPv4.Length; remoteIPAddress.CopyOut(header.Array, header.Start + o); o += IPv4.Length; // calculate checksum ushort chk = IpHeader.CalculateChecksum(header, offset, IpHeader.Size); header[offset + 10] = (byte)(((ushort)chk) >> 8); header[offset + 11] = (byte)(((ushort)chk) & 0xff); //write the udp header header[o++] = (byte)(((ushort)localPort) >> 8); header[o++] = (byte)(((ushort)localPort) & 0xff); header[o++] = (byte)(((ushort)remotePort) >> 8); header[o++] = (byte)(((ushort)remotePort) & 0xff); ushort udpLength = (ushort)(UDPHeader.Size + payloadLength); header[o++] = (byte)(((ushort)udpLength) >> 8); header[o++] = (byte)(((ushort)udpLength) & 0xff); // udp checksum (forget for now) header[o++] = 0; header[o++] = 0; UDPHeader.SetUdpChecksum(header, data, EthernetHeader.Size, udpLength); }