これは Python で実装された TCP/IP ネットワークスタックです。 Berkeley Packet Filter (BPF) を使用してローレベルなパケット処理を行い、OSI 参照モデルの第 2 層 (データリンク層) から第 7 層 (アプリケーション層) までの各プロトコルを実装しています。
本実装はネットワークプロトコルの学習と理解を目的として作成された、フルスクラッチのTCP/IPスタックです。
asyncio
をベースにした非同期処理で効率的なネットワーク通信を実現しています。
- プロトコルスタック: ARP、IPv4、ICMP、UDP、TCP、DNSの実装
- 非同期処理:
asyncio
による高パフォーマンスな並行処理 - マルチプラットフォーム対応: macOS, Linux (,Windows) 用のドライバを提供
- ローレベルアクセス: Berkeley Packet Filter (BPF) による直接的なパケット制御
- TLS 対応: セキュアな通信のための TLS セッション
Layer | - |
---|---|
6 ~ 7 | アプリケーション層 (DNS 解決, HTTP 通信, TLS セッション) |
5 | セッション層 (TLS セッション管理) |
4 | トランスポート層 (TCP, UDP) |
3 | ネットワーク層 (IPv4, ICMP, ARP) |
2 | データリンク層 (Ethernet フレーム処理) |
(1 ~ ) 2 | 物理層 (BPF ドライバ, プラットフォーム固有) |
tcp-ip/
├── main.py # エントリーポイント
├── pyproject.toml # プロジェクト設定
├── uv.lock # 依存関係ロックファイル
└── tcpip/ # メインパッケージ
├── logging_config.py # カラー対応ログ設定
├── core/ # プロトコル実装
│ ├── arp.py # ARP プロトコル
│ ├── dns.py # DNS 解決
│ ├── ethernet.py # Ethernet フレーム
│ ├── icmp.py # ICMP (ping)
│ ├── ip.py # IPv4 プロトコル
│ ├── tcp.py # TCP プロトコル
│ ├── udp.py # UDP プロトコル
│ └── utils.py # 共通ユーティリティ
├── drivers/ # OS 固有ドライバ
│ ├── base_driver.py # 抽象ドライバインターフェース
│ ├── macos_driver.py # macOS BPF ドライバ
│ ├── linux_driver.py # Linux RAW ソケット ドライバ
│ └── windows_driver.py # Windows ドライバ
└── interface/ # 高レベル API
├── stack_controller.py # メインスタック制御
└── tls_session.py # TLS セッション管理
- ARP (Address Resolution Protocol): IPv4 アドレスから MAC アドレスへの解決、キャッシュ
- IPv4: パケット生成・解析、ルーティング、フラグメンテーション対応
- ICMP: Echo Request/Reply (ping機能)、エラーメッセージ処理
- UDP: ユーザーデータグラムプロトコル、チェックサム検証
- TCP: 信頼性のある接続指向通信、3-way handshake、データ転送、接続終了
- DNS: ドメイン名解決、A レコード問い合わせ
- Ping: ICMP Echo を使用したネットワーク到達性テスト
- DNS解決: ドメイン名からIPアドレスへの変換
- TCP接続: HTTP 通信等の接続指向通信
- TLS通信: セキュアな暗号化通信
基本的には main.py
を書き換える形で使用できます。
# 管理者権限が必要, 外部パッケージ依存なし
sudo python main.py
raw ソケットや BPF へのアクセスには管理者権限が必要です。
本実装は asyncio
をベースに非同期なアーキテクチャを使用しています:
- 非同期 I/O: パケット送受信処理の並行実行
- イベントループ統合: BPF ファイルディスクリプタの効率的な監視
- Future/Awaitable: 応答待ちの非同期処理
- コールバック機構: プロトコル固有の処理分散
受信パケット → BPF → Ethernet → IPv4 → [TCP/UDP/ICMP] → アプリケーション
送信データ ← BPF ← Ethernet ← IPv4 ← [TCP/UDP/ICMP] ← アプリケーション
各 OS に対応したドライバを提供:
- macOS: Berkeley Packet Filter (
/dev/bpf*
)- 多分動く、少なくとも私の環境では...
- Linux: Raw Socket (
AF_PACKET
)- 動作未確認
- Windows: WinPcap/Npcap
- 未実装、スタブのみ
階層化された色付きログシステム:
# コンポーネント別ログレベル設定
"tcpip.stack": logging.INFO,
"tcpip.arp": logging.INFO,
"tcpip.tcp": logging.INFO,
"tcpip.dns": logging.INFO,
"tcpip.drivers.bpf": logging.DEBUG,
# 開発用依存関係のインストール
uv sync --group dev
# フォーマット
isort tcpip/ && black tcpip/
# 型チェック
mypy .
# lint
flake8 .
tcpip/core/
に新しいプロトコルファイルを作成StackController
にプロトコル処理を統合- 必要に応じて新しいドライバサポートを追加
BaseDriver
を継承した新しいドライバクラスを作成- OS 固有の raw ソケット API を実装
tcpip/drivers/
に追加
- Python: 3.12 以上
- OS: macOS, Linux (,Windows)
- 権限: 管理者権限 (raw ソケットアクセスのため)
- ネットワーク: アクティブなネットワークインターフェース
- 教育目的: 本実装は学習用途を想定しており、本番環境での使用は推奨されません
- セキュリティ: raw ソケットの使用により高い権限が必要です
- パフォーマンス: 教育的な可読性を優先しているため、高負荷環境には適していません
- 互換性: 標準的な TCP/IP スタックとの完全な互換性は保証されません
症状: test_https.py
実行時、TLS ハンドシェイク開始直後にサーバーから RST セグメントを受信し、接続が切断される
詳細:
- TCP 接続 (3-way handshake) は正常に確立される
- TLS Client Hello (517 bytes) 送信直後に RST セグメントを受信
- 複数のテストサイト (example.com, httpbin.org, www.google.com) で同様の問題が発生
根本的な原因: 独自 TCP/IP スタック実装と Python 標準 ssl の組み合わせによるプロトコルレベル不整合が原因と考えられます:
- TCPレベルでの微細な実装差異 (シーケンス番号管理、ウィンドウサイズ、TCP オプション等)
- IPヘッダーのフィールド値や計算方法の違い
- サーバー側のセキュリティ機構が異常なトラフィックパターンとして検出しRST送信
修正予定:
- TCP 実装の RFC 準拠性向上
- TLS セッション管理の改善
- プロトコル互換性テストの追加
このプロジェクトは教育目的で作成されたオープンソースソフトウェアであり、MITライセンスの下で提供されています。
- [最優先] 不具合の修正
- IPv6 サポート
- より多くの ICMP メッセージタイプ
- TCP の高度な機能 (ウィンドウスケーリング、SACK等)
- ネットワーク可視化
- パケットキャプチャ・解析