public TcpPacket(IIpPacket ipPacket) { if (ipPacket == null) { throw new ArgumentNullException(nameof(ipPacket)); } if (ipPacket.Protocol != IpProtocol.TCP) { throw new ArgumentOutOfRangeException(nameof(ipPacket.Protocol)); } this.RawData = ipPacket.Payload; var span = this.RawData.Span; this.SourcePort = span.ReadUInt16BigEndian(Offsets.SourcePort); this.DestinationPort = span.ReadUInt16BigEndian(Offsets.DestinationPort); this.SequenceNumber = span.ReadUInt32BigEndian(Offsets.SequenceNumber); this.AcknowledgmentNumber = span.ReadUInt32BigEndian(Offsets.AcknowledgmentNumber); // ushort containing Data Offset (aka Header Length) in the first 4 bits, and Control Flags in the following 12 bits var dataOffsetAndFlags = span.ReadUInt16BigEndian(Offsets.DataOffsetAndFlags); // Data Offset (aka Header Length) is encoded as the number of 32-bit words (4 bytes) this.DataOffset = (ushort)(BinaryHelper.ReadBits(dataOffsetAndFlags, 0, 4) * 4); this.Payload = this.RawData.Slice(this.DataOffset); this.ControlFlags = (TcpControlFlags)BinaryHelper.ReadBits(dataOffsetAndFlags, 4, 12); this.Window = span.ReadUInt16BigEndian(Offsets.Window); this.Checksum = span.ReadUInt16BigEndian(Offsets.Checksum); this.UrgentPointer = span.ReadUInt16BigEndian(Offsets.UrgentPointer); // TODO: Parse Options }
public RawPacket(IIpPacket ipPacket) { if (ipPacket == null) { throw new ArgumentNullException(nameof(ipPacket)); } this.RawData = ipPacket.Payload; }
/// <summary> /// Creates UDP datagram based on the specified IP packet. /// </summary> /// <param name="ipPacket">A source IpPacket Object that contains a UDP datagram.</param> /// <param name="reuseOriginalBuffer">A flag that determines if the original packet's buffer needs to be reused.</param> /// <returns>A new UdpDatagram instance.</returns> /// <exception cref="System.ArgumentNullException">ipPacket is null</exception> /// <exception cref="System.NotSupportedException">Only UDP packets are supported.</exception> /// <exception cref="System.ArgumentOutOfRangeException">ipPacket.PacketData is empty.</exception> public static UdpDatagram ToUdpDatagram(this IIpPacket ipPacket, bool reuseOriginalBuffer = true) { if (ipPacket == null) { throw new ArgumentNullException("ipPacket"); } if (ipPacket.ProtocolType != ProtocolType.Udp) { throw new NotSupportedException("Only UDP packets are supported."); } if (ipPacket.PacketData.Count <= 0) { throw new ArgumentOutOfRangeException(); } var packetData = ipPacket.PacketData.AsByteArraySegment(); UdpDatagramHeader udpDatagramHeader = null; if (ipPacket.PacketData.Count > 8) { udpDatagramHeader = new UdpDatagramHeader( packetData.Array.ReadNetOrderUShort(packetData.Offset), packetData.Array.ReadNetOrderUShort(2 + packetData.Offset), packetData.Array.ReadNetOrderUShort(4 + packetData.Offset), packetData.Array.ReadNetOrderUShort(6 + packetData.Offset)); } ArraySegment <byte> udpData; if (reuseOriginalBuffer) { udpData = new ArraySegment <byte>( packetData.Array, packetData.Offset + 8, packetData.Count - 8); } else { var ipOptionsDataArray = new byte[packetData.Count - 8]; Array.Copy(packetData.Array, packetData.Offset + 8, ipOptionsDataArray, 0, packetData.Count - 8); udpData = new ArraySegment <byte>(ipOptionsDataArray); } var udpDatagram = new UdpDatagram { PacketHeader = ipPacket.PacketHeader, UdpDatagramHeader = udpDatagramHeader, UdpData = udpData, ReceivedTime = ipPacket.ReceivedTime }; return(udpDatagram); }
/// <summary> /// Builds a transport-layer packet from an IP packet payload /// </summary> public ITransportPacket Parse(IIpPacket ipPacket) { return(ipPacket.Protocol switch { IpProtocol.TCP => new TcpPacket(ipPacket), IpProtocol.UDP => new UdpPacket(ipPacket), IpProtocol.ICMP => new IcmpPacket(ipPacket), // Other transport-layer packet types are not yet supported _ => null });
public IcmpPacket(IIpPacket ipPacket) { if (ipPacket == null) { throw new ArgumentNullException(nameof(ipPacket)); } if (ipPacket.Protocol != IpProtocol.ICMP) { throw new ArgumentOutOfRangeException(nameof(ipPacket.Protocol)); } this.RawData = ipPacket.Payload; var span = this.RawData.Span; // TODO: Parse Type, Code and Value this.Checksum = span.ReadUInt16BigEndian(Offsets.Checksum); this.Payload = this.RawData.Slice(Offsets.Payload); }
public UdpPacket(IIpPacket ipPacket) { if (ipPacket == null) { throw new ArgumentNullException(nameof(ipPacket)); } if (ipPacket.Protocol != IpProtocol.UDP) { throw new ArgumentOutOfRangeException(nameof(ipPacket.Protocol)); } this.RawData = ipPacket.Payload; var span = this.RawData.Span; this.SourcePort = span.ReadUInt16BigEndian(Offsets.SourcePort); this.DestinationPort = span.ReadUInt16BigEndian(Offsets.DestinationPort); this.Length = span.ReadUInt16BigEndian(Offsets.Length); this.Checksum = span.ReadUInt16BigEndian(Offsets.Checksum); this.Payload = this.RawData.Slice(Offsets.Payload); }