320 likes | 448 Views
ネットワークプログラミング ( CS-B3 選択必修). 峰野博史 mineno@inf.shizuoka.ac.jp. 参考書. などなど. ネットワーク OS. ネットワーク機器などを制御する機能を備えた OS 最近の PC 向け OS は全てネットワーク OS 機能を搭載 様々な部品(モジュール)が階層的に組み合わされてネットワークシステムを構築 特定の機能や役割を担う機能ブロックのことで,通常は他のモジュールと取り換え可能. ネットワークソフトウェアの概要. OS 内部のネットワークソフトウェア. トランスポートモジュール
E N D
ネットワークプログラミング(CS-B3 選択必修)ネットワークプログラミング(CS-B3 選択必修) 峰野博史 mineno@inf.shizuoka.ac.jp
参考書 などなど
ネットワークOS • ネットワーク機器などを制御する機能を備えたOS • 最近のPC向けOSは全てネットワークOS機能を搭載 • 様々な部品(モジュール)が階層的に組み合わされてネットワークシステムを構築 • 特定の機能や役割を担う機能ブロックのことで,通常は他のモジュールと取り換え可能 ネットワークソフトウェアの概要
OS内部のネットワークソフトウェア • トランスポートモジュール • TCP/UDPの機能を実現し,始点ホストと終点ホストの内部で動作 • 最近は,ほぼ全てのルータに搭載されている • インターネットモジュール • IPの機能を実現し,経路上の全てのルータ内部で動作 • デバイスドライバ • NICを制御し,パケットの送信処理,パケットの受信処理
プロトコルスタックとパケットの処理 FCS (Frame Check Sequence)
通信開始時のアドレス変換処理① • アプリケーションレベル: ホスト名 • トランスポートレベル: ポート番号 • IPレベル: IPアドレス • Ethernetレベル: MACアドレス 2.サービス名からポート番号を調べる 1.ホスト名からIPアドレスを調べる
通信開始時のアドレス変換処理② • IPアドレスから,次に送るべきホストやルータを決定 > route PRINT • IPアドレスから,MACアドレスを調べる > arp -a ARP (Address Resolution Protocol)
詳細 TCB (Transmission Control Block) ARP (Address Resolution Protocol) FCS (Frame Check Sequence)
クライアントサーバモデル • クライアント: 処理を要求するプログラム • サーバ: 要求を受けて処理するプログラム MTA (Mail Transfer Agent), Web Proxy Server など
ソケットを用いたシステムコールと内部処理 • ソケット • アプリケーションとトランスポートモジュールとのインタフェース • 関数呼び出しのような形でシステムコールを呼び出しメッセージ送受信 • アプリケーション • ユーザモードで動作 • 資源へのアクセスは制限され,許可外にアクセスすると”Segmentation fault (core dumped)”し,システム動作には影響を与えない • カーネル • カーネルモードで起動 • システム起動後にメモリに常駐するOSの中心部 • メモリ保護機能は働かず,全ての資源にアクセス可能で,不正処理時はシステム全体へ波及する可能性がある • バッファ • データを一時的に記憶しておくメモリ領域(有限) • キュー(待ち行列) • FIFOに分類されるバッファの一形態
sendシステムコールと内部処理 • sendシステムコールは,OSに「送信処理を依頼する」だけで,実際の送信処理はOS内部の様々なモジュールを介して実行 • ソケットモジュールは,ユーザのメモリ空間に存在する送信メッセージをカーネルのメモリ空間へコピーし,ソケットのバッファ(送信キュー)へ渡す • TCPのバッファが空いている場合,ソケットのバッファにたまっているメッセージを順番にTCPモジュールのバッファ(TCP送信キュー)へ入れ,TCPに処理を任せる.TCPのバッファが一杯の場合は,TCPのバッファに空きができるまで処理を待つ • TCPモジュールがバッファに格納されているメッセージをIPモジュールに渡す時には,チェックサムを計算したりポート番号を挿入したTCPヘッダを付加して,TCPセグメントの形にしてからIPモジュールのバッファ(IP送信キュー)へ入れる • IPモジュールは,ルーティング等の処理や始点・終点IPアドレスを挿入したIPヘッダを付加して,IPパケットをNICデバイスドライバのバッファ(I/F送信キュー)へ入れる • NICデバイスドライバは,始点・終点MACアドレスを挿入したMACヘッダとFCSを含んだMACトレイラを付加して,MACフレームをバッファ(NIC送信キュー)へ入れる • MACフレームの送信
recvシステムコールと内部処理 • recvシステムコールは,データの受信処理をしているわけではなく「ソケットのキューにたまっている受信データを取り出している」にすぎない • NICがMACフレームを受信 • ハードウェア割込み(IRQ: Interrupt ReQuest)によって,それまで行われていた処理は一時的に中断し,ハードウェア割込みで指定されたOS内部のデバイスドライバへ処理を渡すために,受信したMACフレームをバッファ(I/F受信キュー)へ入れる • NICデバイスドライバは,MACフレームヘッダ・トレイラの除去と処理を行い,取り出したIPパケットをバッファ(IP受信キュー)へ入れ,ソフトウェア割込みを発行(上位層のIP受信キューが一杯であれば,IPパケットを渡さずに破棄) • ソフトウェア割込みされたIPモジュールを起動し,IPヘッダの除去と処理を行い,取り出したTCPセグメントをバッファ(TCP受信キュー)へ入れ,上位層モジュールを呼び出す • 上位層モジュールがTCPならば,TCPモジュールへTCPセグメントを渡し,TCPヘッダの除去と処理を行い,取り出したメッセージをバッファ(ソケット受信キュー)へ格納(アプリケーションがデータを受信可能に) • recvが実行されていれば,recv処理を実行し,アプリケーションのバッファに受信メッセージがコピーされる.recvが実行されてなければ,recv実行までバッファに格納されたまま残る(受信データが無ければプログラムは処理を停止しブロックされる)
バッファ管理とメモリコピー,ポインタ • メモリ上のパケットをキューに出し入れする時は,メモリコピーの回数ができるだけ少なくなるように処理 • キューの出し入れにメモリコピーをすると,処理に時間がかかり,通信性能が低下 • ポインタによる参照でキューへの出し入れを実現 • ヘッダ処理は,ポインタによるリスト構造の追加・削除で実現 • Linux: skbuff構造体 • BSD: mbuf構造体 • ポインタとデータ長
Raw IPとデータリンクアクセスI/F • ソケットI/Fでは,IPパケットやMACフレームを直接,送受信することも可能 • rawソケット,raw IPとも呼ぶ • MacOS/FreeBSDでは,BPF(BSD Packet Filter)を用いる • pingコマンドで利用するICMPエコー要求や,ルーティングプロトコルのOSPF等で利用
多重化とバッファ①(キュー) • クライアントから複数要求があっても,同時に処理できるのは1つだけ • 到着順にキューに入れられて順番に処理
多重化とバッファ②(マルチプロセス) • 処理要求を受け付ける度に子プロセスを生成し,応答処理を子プロセスに任せる(fork) • 通常,1つの処理要求に対して1つのプロセスが処理担当 • 各プロセスはメモリ保護されて並列動作するため安定 • ただし,一般的にプロセスの切り替えはスレッドの切り替えに比べて遅いため,プロセス切り替え(コンテキストスイッチ)が頻繁に起きる場合には処理性能が低下
多重化とバッファ③(マルチスレッド) • 処理要求を受け付ける度にスレッドを生成し,応答処理をスレッドに任せる(pthread) • スレッドは,1つのプロセスの中で並列実行する処理形態で,並列処理される部分はメモリ保護されないため,スレッドが1つでも異常動作すると,プロセス全体が誤動作する可能性がある • スレッド切り替えはプロセス切り替えよりも短時間
多重化とバッファ④(selectシステムコール) • 同一のプロセスやスレッドで,受信したメッセージを区別しながら処理 • それぞれの要求処理が無関係でなく,関係がある場合によく利用される • 同一クライアントから複数のコネクションをサーバと確立して,処理要求を送信する場合など
プログラムとプロトコル • プログラム=データ構造+アルゴリズム • プロトコル=パケットの構造+動作の定義 • 1年生:TCP/IPネットワークコンピューティング入門 • どんなブラックボックスがあるか一通り認識してもらう • 2年生:コンピュータネットワーク講義 • 各種講義でブラックボックスの中身を勉強していく • 3年生:ネットワークプログラミング演習 • 実験系科目で中身をより深く体感してもらう
ARPの動作(要求) Ethenetブロードキャスト アドレス ARPパケット ターゲットハードウェアアドレス(不明:知りたい) ターゲットプロトコルアドレス ARP (Address Resolution Protocol)
ARPの動作(応答) ARPテーブルに書込み (数分間経過後に消去)
IPの動作 【ルーティングテーブルの書式】 「IPアドレス」/「ネットワーク部のビット長」 「転送先」 宛先IPアドレスの先頭ビットから「ネットワーク部のビット長」を取り出し,「IPアドレス」に一致したら「転送先」へ送る
IPフラグメント • IPデータグラムを複数のフレームへ分割 • フラグメント処理(リアセンブルは終点ノードでのみ) • データリンク毎に送信可能な最大のフレームサイズが決まっているため • MTU: Maximum Transmission Unit • Ethernetは1500オクテット,FDDIは4352オクテット,IP over ATMは9180オクテット,PPPoEは1492オクテット,Ethernetジャンボフレームは8000~15000オクテット等 IPヘッダのフォーマット
IPフラグメントの問題点 • 途中ルータでフラグメント処理するのは問題 • ルータの負荷上昇 • フラグメントされたIPデータグラム喪失時の転送効率の低下(通常,リアセンブルのためにしばらくバッファにためられるが,その後は全て廃棄) • 昨今主流のFTTHやADSL等で利用されるPPPoEのMTUは最大1492オクテットのため,一般的なEthenetの1500オクテットでは,IPデータグラムのフラグメントが発生するか,経路MTU探索が実行され通信性能が低下する場合がある • NTT東日本の場合,1454 or 1448 が最適値らしい • 1オクテット ≅ 8ビット (=1byte) • 実は1byteが何bitかは文脈に依存するため,通信分野ではオクテットをよく使っている
バイトオーダ • 2バイト以上の整数データをメモリに格納する時の順序(CPUに依存) • ビッグエンディアン • データの値の最上位ビットがアドレスの先頭(小さい番地)に来るよう格納 • SunのSPARC,稼働CPUに関係なくJava仮想マシン • リトルエンディアン • データの値の最上位ビットがアドレスの最後尾(大きい番地)に来るよう格納 • インテルのx86系など • ネットワークバイトオーダ • ネットワーク中を流れるパケットでは,ビッグエンディアンと同じように,上位ビットを先頭に配置する順番 • htonl()で「hostのバイトオーダをnetworkバイトオーダへlong型で変換」でき,コンピュータによらずコンパイラが正しく変換してくれる
バイトスワップ処理 • ネットワークバイトオーダ(ビッグエンディアン)をリトルエンディアンへ変換する(バイトスワップ) • ビットシフト演算によるバイトスワップ • 「<<」(上位bit(左)へシフト),「>>」(下位bit(右)へシフト) • 一般的にCPUは算術演算よりもシフト演算の方が高速(実は,コンパイラで最適化されてシフト演算に置き換えられているのだが) • 左シフトで2で乗算,右シフトで2で除算した結果と同じになる • 2つのレジスタを用いたバイトスワップ • 上位bitと下位bitを入れ替えて,別のレジスタへデータ転送 元の16bit長データを右に8bit分シフトしたデータ 元の16bit長データを左に8bit分シフトしたデータ 2つのレジスタを用いて上位8bitと下位8bitを入れ替え バイトスワップ可能 論理和をとれば バイトスワップ完了
UDP(User Datagram Protocol) • 途中でデータ欠損しても問題の少ない通信でよく利用 • VoIP(Voice over IP),ビデオストリーミング • TCPに比べ圧倒的に処理が軽い • IPの機能をほとんどそのまま利用 • TCPが提供するような機能を自前で用意するアプリケーションでは,UDPを使う方が無駄を省ける UDPヘッダのフォーマット struct udphdr { u_short uh_sport; /* source port */ u_short uh_dport; /* destination port */ u_short uh_ulen; /* udp length */ u_short uh_sum; /* udp checksum */ } UDPヘッダの構造体
TCP(Transmission Control Protocol) • 信頼性の提供 • 3-wayhandshake • シーケンス番号とAck • チェックサム • ウィンドウフロー制御 • 送信バッファ,受信バッファ struct tcphdr { u_short th_sport; /* source port */ u_short th_dport; /* destination port */ u_short th_seq; /* sequence number */ u_short th_ack; /* acknowledgement number */ # if BYTE_ORDER == LITTLE_ENDIAN u_int th_x2:4, /* (unused) */ th_off:4; /* data offset */ #endif #if BYTE_ORDER == BIG_ENDIAN u_int th_off:4, /* data offset */ th_x2:4; /* (unused) */ #endif u_char th_flags; u_short th_win; /* window */ u_short th_sum; /* checksum */ u_short th_urp; /* urgent pointer */ }; TCPヘッダのフォーマット TCPヘッダの構造体
参考書 などなど