ffalcinelli/pydivert
GitHub: ffalcinelli/pydivert
PyDivert 是 Windows 网络驱动 WinDivert 的 Python 绑定,支持在内核层面实时捕获、修改和丢弃网络流量数据包。
Stars: 238 | Forks: 44
# PyDivert
[](https://github.com/ffalcinelli/pydivert/actions/workflows/ci.yml)
[](https://codecov.io/gh/ffalcinelli/pydivert)
[](https://pypi.python.org/pypi/pydivert)
[](https://ffalcinelli.github.io/pydivert/)
[](https://pypi.python.org/pypi/pydivert)
[](https://pypi.python.org/pypi/pydivert)
[](https://github.com/ffalcinelli/pydivert/blob/main/LICENSE)
[](https://security.snyk.io/package/pip/pydivert)
**PyDivert** 是 [WinDivert](https://reqrypt.org/windivert.html) 的一个强大的 Python 绑定。WinDivert 是一个 Windows 驱动程序,允许用户模式应用程序捕获、修改和丢弃发送到或来自 Windows 网络栈的网络数据包。
## 特性
- **捕获**匹配特定过滤器的网络数据包。
- **动态修改**数据包的头部和有效载荷。
- **丢弃**不需要的数据包。
- **注入**新的或修改过的数据包到网络栈中。
- **现代 Python 支持**:与 `asyncio` 和结构化模式匹配 (PEP 634) 全面集成。
- **支持 WinDivert 2.2+** 的高级功能(FLOW、SOCKET 和 REFLECT 层)。
- **内置二进制文件**:无需手动安装 WinDivert;已包含 64 位的 DLL 和驱动程序。
## 要求
- **Python 3.10+** (64 位)
- **Windows 11** (64 位)
- **管理员权限**(与 WinDivert 驱动程序交互所需)
## 安装说明
使用 `pip` 安装 PyDivert:
```
pip install pydivert
```
或者使用 [uv](https://github.com/astral-sh/uv):
```
uv add pydivert
```
## 快速入门
主要的入口点用于捕获的 `pydivert.WinDivert` 和用于操作的 `pydivert.Packet`。
### 基本捕获和重新注入
```
import pydivert
# 仅捕获目标端口为 80 的 TCP 数据包(HTTP 请求)
with pydivert.WinDivert("tcp.DstPort == 80") as w:
for packet in w:
print(f"Captured: {packet}")
w.send(packet) # Re-inject the packet back into the stack
```
当你调用 `.recv()`(或对 `WinDivert` 对象进行迭代)时,数据包会从 Windows 网络栈中**移出**。除非你显式调用 `.send(packet)`,否则它将无法到达其目的地。
### 一流的 `asyncio` 支持
PyDivert 3.0+ 使用现代的 `async with` 和 `async for` 语法原生支持 `asyncio`。
```
import asyncio
import pydivert
async def main():
# Asynchronously capture packets
async with pydivert.WinDivert("tcp.DstPort == 80") as w:
async for packet in w:
print(f"Async captured: {packet}")
await w.send_async(packet)
if __name__ == "__main__":
asyncio.run(main())
```
## 常见用例
### 1. 结构化模式匹配 (PEP 634)
使用简洁的 `match/case` 语法过滤和分析数据包。
```
import pydivert
from pydivert.packet import Packet
from pydivert.packet.tcp import TCPHeader
with pydivert.WinDivert("tcp") as w:
for packet in w:
match packet:
case Packet(tcp=TCPHeader(dst_port=80)):
print("HTTP Traffic")
case Packet(tcp=TCPHeader(dst_port=443)):
print("HTTPS Traffic")
w.send(packet)
```
### 2. 简单防火墙(丢弃数据包)
只需不调用 `.send(packet)`,即可有效地丢弃该数据包。
```
import pydivert
# 阻止来自特定 IP 地址的所有流量
with pydivert.WinDivert("ip.SrcAddr == 1.2.3.4") as w:
for packet in w:
print(f"Blocking packet from {packet.src_addr}")
# Packet is dropped here
```
### 3. 有效载荷修改
你可以检查或修改数据包有效载荷的原始字节。
```
import pydivert
# 筛选带有 payload 的 TCP 数据包
with pydivert.WinDivert("tcp.PayloadLength > 0") as w:
for packet in w:
if b"secret-token" in packet.payload:
# Redact the token
packet.payload = packet.payload.replace(b"secret-token", b"REDACTED")
w.send(packet)
```
## 数据包完整性与校验和
PyDivert 可以自动验证和重新计算网络校验和。
- **`packet.is_checksum_valid`**:如果数据包中的所有校验和(IP、TCP、UDP、ICMP)都正确,则返回 `True`。
- **`packet.recalculate_checksums()`**:根据当前的头部和有效载荷值重新计算所有校验和。
```
if not packet.is_checksum_valid:
print("Corrupted packet detected!")
packet.recalculate_checksums()
```
## 常见数据包属性
`pydivert.Packet` 对象提供了对常见字段的便捷访问:
- **IP 层**:`packet.src_addr`、`packet.dst_addr`、`packet.ip.ttl`、`packet.ip.protocol`
- **TCP/UDP 层**:`packet.src_port`、`packet.dst_port`、`packet.tcp.flags`
- **有效载荷**:`packet.payload`(字节)
- **元数据**:
- **`timestamp`**:捕获时间 (QueryPerformanceCounter)。
- **`is_loopback`**、**`is_impostor`**、**`is_sniffed`**:布尔标志。
- **`interface`**:捕获接口的索引。
- **`direction`**:`Direction.INBOUND` 或 `Direction.OUTBOUND`。
详细的协议头可以通过 `packet.ipv4`、`packet.ipv6`、`packet.tcp`、`packet.udp` 和 `packet.icmp` 访问。
## 高级用法
### WinDivert 层
- `Layer.NETWORK`(默认):IP 数据包。
- `Layer.FLOW`:连接事件。
- `Layer.SOCKET`:套接字级别的事件。
- `Layer.REFLECT`:反射事件。
### 标志
- `Flag.SNIFF`:监控模式(嗅探)。
- `Flag.DROP`:默认丢弃数据包。
- `Flag.FRAGMENTS`:捕获所有 IP 分片。
- `Flag.RECV_ONLY` / `Flag.SEND_ONLY`:受限句柄。
## 过滤器语言
PyDivert 使用 WinDivert 过滤器语言来选择要捕获的数据包。有关语法和可用字段的详细参考,请参阅[过滤器语言指南](#windivert-filter-language)。
有关原始的技术参考,请访问[官方 WinDivert 文档](https://reqrypt.org/windivert-doc.html#filter_language)。
## WinDivert 版本兼容性
| PyDivert | WinDivert |
| --- | --- |
| 3.0.0+ | 2.2.2 (捆绑) - 完全支持现代元数据和层 |
## 开发
1. 克隆仓库。
2. 安装依赖:`uv sync --extra test --extra docs`
3. 运行测试(需要管理员权限):`uv run pytest`
### 使用 Vagrant 进行测试
由于 WinDivert 需要 Windows 环境,请使用 **Vagrant** 在 Windows 11 虚拟机上运行测试:
```
vagrant up
vagrant powershell -c '$env:UV_PROJECT_ENVIRONMENT="C:/pydivert_venv"; cd C:/pydivert; uv run pytest'
```
## API 参考
完整的 API 文档可在 [https://ffalcinelli.github.io/pydivert/](https://ffalcinelli.github.io/pydivert/) 获取。
## 许可证
PyDivert 在 [LGPL-3.0-or-later](https://github.com/ffalcinelli/pydivert/blob/main/LICENSE-LGPL-3.0-or-later) 和 [GPL-2.0-or-later](https://github.com/ffalcinelli/pydivert/blob/main/LICENSE-GPL-2.0-or-later) 下双重许可。
## 安全
PyDivert 致力于安全保障,并使用 [Snyk](https://snyk.io/) 进行持续的漏洞扫描。有关我们的安全实践以及如何报告漏洞的更多详细信息,请参阅[安全政策](#security-policy)。
标签:asyncio, ATT&CK 框架, MacOS取证, Python, Python绑定, Wildcard支持, WinDivert, Windows 11, Windows驱动, 中间人攻击, 异步IO, 数据包注入, 数据包过滤, 无后门, 欺骗, 流量控制, 系统权限, 网络嗅探, 网络安全, 网络层, 网络开发, 网络拦截, 网络数据包, 计算机取证, 逆向工具, 防御绕过, 防火墙, 隐私保护