/// <summary> /// Packet data is only valid until the next call /// </summary> /// <param name="e"></param> /// <returns>Status of the operation</returns> public GetPacketStatus GetNextPacket(out PacketCapture e) { ThrowIfNotOpen(); while (true) { bool ret; WinDivertAddress addr; uint readLen; unsafe { fixed(byte *p = buffer) { ret = WinDivertNative.WinDivertRecv(Handle, new IntPtr(p), (uint)buffer.Length, out readLen, out addr); } } if (!ret) { var err = Marshal.GetLastWin32Error(); if (err == ERROR_INSUFFICIENT_BUFFER) { // Increase buffer size buffer = new byte[buffer.Length * 2]; continue; } if (err == ERROR_NO_DATA) { e = default; return((GetPacketStatus)(-err)); } ThrowWin32Error("Recv failed", err); } var timestamp = new PosixTimeval(BootTime + TimeSpan.FromTicks(addr.Timestamp)); var data = new ReadOnlySpan <byte>(buffer, 0, (int)readLen); var header = new WinDivertHeader(timestamp) { InterfaceIndex = addr.IfIdx, SubInterfaceIndex = addr.SubIfIdx, Flags = addr.Flags }; e = new PacketCapture(this, header, data); return(GetPacketStatus.PacketRead); } }
public RawCapture GetNextPacket() { ThrowIfNotOpen(); Span <byte> buffer = stackalloc byte[4096]; while (true) { bool ret; WinDivertAddress addr; uint readLen; unsafe { fixed(byte *p = buffer) { ret = WinDivertNative.WinDivertRecv(Handle, new IntPtr(p), (uint)buffer.Length, out readLen, out addr); } } if (!ret) { var err = Marshal.GetLastWin32Error(); if (err == ERROR_INSUFFICIENT_BUFFER) { // Increase buffer size buffer = stackalloc byte[buffer.Length * 2]; continue; } if (err == ERROR_NO_DATA) { return(null); } ThrowWin32Error("Recv failed", err); } var timestamp = new PosixTimeval(BootTime + TimeSpan.FromTicks(addr.Timestamp)); var data = buffer.Slice(0, (int)readLen).ToArray(); var raw = new WinDivertCapture(timestamp, data) { InterfaceIndex = addr.IfIdx, SubInterfaceIndex = addr.SubIfIdx, Flags = addr.Flags, }; return(raw); } }