Networking and Internet
2台以上のマシンが繋がっている状態をネットワークという
Page *
Page * Copyright: MCC Java Network Programming
3
Protocol
あるPCから別のPCに情報を送る際に、プロトコルというものが使われる データのパケット(小包)をやり取りすることでコンピュータ同士は通信す る インターネット上で別のPCに情報を送信する際に、インターネットプロト コル(IP)というネットワークプロトコルが使われる Protocol – プロトコルLayered Protocols – 層状に重なったプロトコル アプリケーシ ョン プロトコル プレゼンテーショ ン プロトコル セッション プロトコル トランスポー ト プロトコル ネットワーク プロトコル データリンク プロトコル フィジカル プロトコル アプリケーション層 プレゼンテーション 層 セッション層 トランスポート層 ネットワーク層 データリンク層 物理層
7
6
5
4
3
2
1
Page * Page * 5 7. アプリケーション層= HTTP, FTP, SMTP, NSF, Telnet, SSH, ECHO, … 6. プレゼンテーション層 = SMB, NCP, … 5. セッション層 = SSH, NetBIOS, RPC, … 4. トランスポート層 = TCP, UDP, … 3. ネットワーク層 = IP, ICMP, IPX
2. データリンク層 = Ethernet, Token Ring, ISDN, … 1. 物理層 = 100BASE-T, 1000BASE-T, 802.11
TCP and UDP
プロトコル:Transport Control Protocol (TCP)とUser Datagram Protocol (UDP)
アプリケーシ ョン プロトコル プレゼンテーショ ン プロトコル セッション プロトコル トランスポー ト プロトコル ネットワーク プロトコル データリンク プロトコル フィジカル プロトコル アプリケーション層 プレゼンテーション 層 セッション層 トランスポート層 ネットワーク層 データリンク層 物理層
7
6
5
4
3
2
1
Page *
Page * 7
複数のPC間で信頼性の高い通信を実
現するためにTCP (Transport Control Protocol)
というコネクション確立型のプロトコル が使われる 使用される例: – HTTP(ウェブページ) – FTP(ファイル転送) – Telnet(遠隔通信) TCP/IP スタック アプリケーション層 (http,ftp,telnet,…) トランスポート層(TCP) ネットワーク層 (IP,..) リンク層 (device driver,..)
データグラムと呼ばれる一個一個の パケットを、別のPCに届いたかどうか
気にせず送信するやり方として、UDP
(User Datagram Protocol) プロトコルがある。 使用される例:
– 時刻サーバー – ピング(Ping)
User Datagram Protocol (UDP)
TCP/IP スタック アプリケーション層 (http,ftp,telnet,…) トランスポート層(UDP,..) ネットワーク層 (IP,..) リンク層 (device driver,..)
Page * Page * 9 TCPやUDPプロトコルでは、受信したデ ータはポート番号によって、コンピュ ータ上で実行しているプロセス(アプリ )ごとに振り分けている サーバー ポート クライ アント TCP TCP or UDP ポート ポート ポート ポート アプリ アプリ アプリ アプリ ポート 番号 データ データ パケット Ports ポート
ポート番号は正の整数で表現できる値(16-bit)をとる 一般的によく使用されるサービスやシステムに必須のプロセスに割り当てられ るポート番号はあらかじめ決められている: – ftp 21/tcp – telnet 23/tcp – smtp 25/tcp – login 513/tcp 任意でユーザーが使用するプロセスやサービスは基本的に1024よりも小さいポ ート番号を使用する Ports ポート
Page *
Page * Copyright: MCC Java Network Programming
11 クライアントPCとサーバーPCの組み方によって、インターネットは様々な サービスを提供する Webブラウザのようなクライアント・プログラムはWebやFTPサービスなどの サーバー・プログラムとの接続を確立する クライアントPCはサーバーに要求を出し、サーバーPCは要求されたサー ビスを提供することでクライアントPCに応答を返す クライアントPCはクライアント・ソケットを介して通信を行い、サーバーPC はサーバー・ソケットを介して通信を行う Client-Server Computing – クライアントPCとサーバーPC
ソケット通信はトランスポート層においてネットワークプログラミングのためのイ ンタフェースを提供する ソケットを使ったネットワーク通信はファイル入出力操作と類似した機能を有し ている – 実際、ソケットの扱いとファイルの扱いは似ている – ファイル入出力操作において使用されるストリームはソケットをベースにした 入出力に応用することもできる ソケットをベースにした通信は言語に依存しない – つまり、Java言語で書かれたソケットプログラムはJava言語やJavaでない言語の どちらのソケットプログラムとも通信できる Sockets – ソケット
Page * Page * 13 あるポートとの接続を確立したソケットを確保したサーバー上において、サーバ ープログラムが起動している サーバーPCはクライアントPCからの接続要求を待つ間、ポートを開いて待ってい る サーバー クライアン ト 接続要求 Socket Communication – ソケット通信 ポート
すべての処理が上手くいくと、サーバーPCは接続を承諾する 承諾している間は、サーバーPCは別のポートに繋がれた新しいソケット を獲得 しないといけない 先ほどまで接続を確立していた元々のソケットが今もなお接続要求を出してい るかどうかをチェックするためにもう一つ新しいソケット(厳密には別のポート番 号のもの)を確保する必要がある サーバ クライアント 接続中 ポート Socket Communication… - ソケット通信(続き) ポー ト ポート
Page * Page * ソケットとは、ネットワーク上で実行している二つのプログラム間における双方 向通信の末端に当たる部分のことを指している 何よりもまずサーバーの処理(ソケットを用意すること)を初めにするべき(TCPは コネクションレス型ではないことを覚えておく) サーバーのIPアドレスやポート番号を指定したクライアント側のソケットによって 、クライアントはサーバーとコンタクトをとる クライアントからコンタクトがあったとき、サーバー側のTCPはクライアントと通信 を計るための新しいソケットを作る • サーバーは複数のクライアントと同時に会話することができる • 元のポート番号はクライアントの識別のために使用している アプリケーションの観点から: TCPネットワークは信頼性があり、クライアントとサ ーバー間でバイトを転送する(パイプを作る)ときによく使われる
ソケットはポート番号と関連しているため、どこにデータを送信す
べきか、その宛先となるアプリケーションを
TCP層で特定すること
ができる
Javaの.netパッケージは次の二つのクラスを用意している:
– ソケット(Socket)
– クライアントプログラム用
– サーバーソケット(ServerSocket)
– サーバープログラム用
Page * Page * 17
ServerSocket(1234)
Socket(“128.250.25.158”, 1234)
出力/書込 ストリーム
入力/読込 ストリーム
“icd.cs.tut.ac.jp”のようにホスト名で書き換えることもできる
Client Server1.
ServerSocketを開く:
ServerSocket server; DataOutputStream os; DataInputStream is;
server = new ServerSocket( PORT );
2
. クライアントからの要求を待つ:
Socket client = server.accept();
3. クライアントと通信するためのI/Oストリームを作る
is = new DataInputStream( client.getInputStream() );
os = new DataOutputStream( client.getOutputStream() );
4. クライアントと実際の通信をする
Receive from client: String line = is.readLine(); Send to client: os.writeBytes("Hello¥n");
Page *
Page * 19
1. Socketオブジェクトを作成する:
client = new Socket( server, port_id );
2. サーバーと通信するためのI/Oストリームを作る.
is = new DataInputStream(client.getInputStream() );
os = new DataOutputStream( client.getOutputStream() );
3. サーバーからの情報を入出力したり、サーバとの通信を行う: – Receive data from the server:
String line = is.readLine();
– Send data to the server:
os.writeBytes("Hello¥n");
4. すべての処理が完了したらソケットを閉じる:
client.close();
// SimpleServer.java: a simple server program import java.net.*;
import java.io.*;
public class SimpleServer {
public static void main(String args[]) throws IOException { // ポート番号1234でネットワークを確立する
ServerSocket s = new ServerSocket(1234);
Socket s1=s.accept(); // 承諾を待つ // ソケットに関連したストリームを取得する
OutputStream s1out = s1.getOutputStream();
DataOutputStream dos = new DataOutputStream (s1out); // 文字を送信!
dos.writeUTF("Hi there");
// 接続を閉じる(サーバーのソケットはそのまま) dos.close();
Page *
Page * 21
// SimpleClient.java: a simple client program import java.net.*;
import java.io.*;
public class SimpleClient {
public static void main(String args[]) throws IOException { // ポート番号1234を開放し、サーバーに接続する
Socket s1 = new Socket("mundroo.cs.mu.oz.au",1234);
// ソケットから入力ファイルハンドルを取得し、情報を読み込む InputStream s1In = s1.getInputStream();
DataInputStream dis = new DataInputStream(s1In); String st = new String (dis.readUTF());
System.out.println(st); // 処理が完了したら、接続を解除し、プログラムを終了する dis.close(); s1In.close(); s1.close(); } }
自分のPCでサーバープログラムを実行する
– < java SimpleServer &
上と同じPCでクライアントプログラムを実行する
– <java SimpleClient Hi there
サーバープログラムを実行する前にクライアント側を実行すると、次のようなエ
ラーが生じる:
– < sockets [1:147] java SimpleClient
Exception in thread "main" java.net.ConnectException: Connection refused at java.net.PlainSocketImpl.socketConnect(Native Method)
at java.net.PlainSocketImpl.doConnect(PlainSocketImpl.java:320)
at java.net.PlainSocketImpl.connectToAddress(PlainSocketImpl.java:133) at java.net.PlainSocketImpl.connect(PlainSocketImpl.java:120)
Page * Page * Exception(例外)って何??? プログラムを実行しているときに、そのプログラムの通常の処理の流れを妨げ るような出来事のことをexception(例外)という どうして Exception Handling(例外処理)をするの?? エラーが生じた時や予期せぬ出来事が起こったときに、適切にプログラムを落 とすことができる プログラムの実行中に問題を解決することができる エラーが起きた時、対応策や回避策等のユーザを支援するための適切なメッ セージを表示することができる Exception Handling – エラー処理
メソッドの中でエラーが生じたとき、そのメソッドはオブジェクトを作ってランタイム システムに渡す
そのオブジェクトはexception object と呼ばれ、エラーに関する情報やエラーの種類、 エラーが生じたときのプログラムの状態などが記載されている
exception objectを作り、ランタイムシステムに渡すことをthrowing an exception と呼ぶ
Java言語におけるエラー処理はTry , Catch や Finally 構文を使って行われる.
Java言語においてすべての種類の例外やエラーを表すスーパークラスは
Page * Page * try { code } キャッチ・ブロック
catch (Exception ex) { < 例外exが生じた時、対処すべきことをここに書く > } キャッチ – エラー処理を行うことで例外に対処する一つの方法 Try Block – トライ・ブロック
try {
Socket client = new Socket(host, port); handleConnection(client);
}
catch(
UnknownHostException
uhe) { System.out.println(“ホストが見つかりませ
ん: " + host); uhe.printStackTrace();
}
catch(
IOException
ioe) {
System.out.println(“入出力エラー: " + ioe); ioe.printStackTrace();
}
Page * Page *
ServerSocket(int port) で生じる IOException
– 任意のポート番号でサーバーソケットを作りたいとき、0番ポートを指定するこ とで、システムが空いているポートを選別して自動的にポート番号を割り振っ てくれる – 自動的に割り振られたポート番号を知りたい場合は getLocalPort() 関数を使って その番号を調べることができる. – 受信する接続 (接続要求) のキューの最大長は50 に設定されている 。これを超えた場合、接続は拒否される 状態: – IOException – ソケットの開放中に入出力エラーが生じたとき – SecurityException – セキュリティソフトがインストールされており、プログラムの動 作が監視されて処理がブロックされてしまう
Conclusion – まとめ
クライアント用やサーバー用のアプリケーションをJavaでプログラミ
ングすることは楽しくもあり、また挑戦的でもある
C言語などの他の言語と比べて、Java言語であれば比較的簡単に
ソケットプログラムを作ることができる
キーワード:
– クライアント、サーバー、TCP/IP、ポート番号、ソケット、Javaのソケ
ット
Page * Page *
Server in Loop: Always up – ループ関数で常に更新させる
// SimpleServerLoop.java: シングルスレッドを用いて常に最新の状態に更新する簡単なサーバープログラムの例: import java.net.*;
import java.io.*;
public class SimpleServerLoop {
public static void main(String args[]) throws IOException { // 1234というポート番号でサービスを登録する
ServerSocket s = new ServerSocket(1234);
while(true) {
Socket s1=s.accept(); // 接続要求を待ち、接続を承諾する // ソケットに関連したコミュニケーションストリームを取得する OutputStream s1out = s1.getOutputStream();
DataOutputStream dos = new DataOutputStream (s1out); // 文字を送信!
dos.writeUTF("Hi there");
// 接続を閉じる(サーバーのソケットはそのまま) dos.close();
Page *
Page * 31
Code: Time Server – TimeServerのソース
import java.io.DataOutputStream; import java.net.*;
import java.util.Date; public class TimeServer {
public static void main(String[] args) throws Exception { ServerSocket server = new ServerSocket(7000); System.out.println("Server is started");
while(true) {
Socket socket = server.accept();
DataOutputStream dos = new DataOutputStream(socket.getOutputStream()); String time = new Date().toString();
dos.writeUTF(time); socket.close(); }
} }
Code: Time Client – TimeClientのソース
import java.io.DataInputStream; import java.io.DataOutputStream; import java.net.Socket;
public class TimeClient {
public static void main(String[] args) throws Exception { Socket socket = new Socket("localhost", 7000);
DataInputStream din = new
DataInputStream(socket.getInputStream()); String time = din.readUTF();
System.out.println(time); }