06. 웹서버에 도착하여 응답 데이터가 웹 브라우저로 돌아간다. - chwyym/Network GitHub Wiki
① Socket Library 구조
- 클라이언트는 접속동작을 수행하고, 서버는 클라이언트의 접속동작을 기다린다.
② 서버의 애플리케이션은 동시에 다수의 클라이언트 PC와 대화한다.
- 클라이언트가 새로 접속할 때마다 새로 서버 프로그램을 작동시켜 1:1로 대화하는 방법을 선택.
① 서버 프로그램 접속을 기다리는 부분과 클라이언트와 대화하는 부분의 둘로 만든다.
② 서버 프로그램을 작동해서 설정 파일 읽기 등의 초기화 동작을 마쳤을 때 접속을 기다리는 부분을 실행한다.
③ 클라이언트가 접속하면 클라이언트와 대화하는 부분을 작동시켜서 그곳에 접속이 끝난 소켓을 건네주어 대화를 진행한다.
※ 서버 OS는 멀티태스크 또는 멀티스레드라는 기능에 의해 다수의 프로그램을 동시에 함께 작동할 수 있다.
※ 이 방법은 클라이언트가 접속했을 때 새로 프로그램을 기동하는 부분에서 다소 시간이 걸리고, 응답 시간이 추가로 소요된다는 단점이 있다. 그래서 미리 클라이언트와 대화하는 몇 개의 부분을 작동
시켜두고 클라이언트가 접속했을 때 클라이언트의 상대를 처리하지 않는 비어있는 것을 찾아 여기에 접속한 소켓을 건네주어 클라이언트와의 대화를 계속하는 방법도 있다.
- 서버 애플리케이션이 Socket 라이브러리를 호출하는 부분의 개요
① 소켓을 만든다.
② 서버측의 소켓과 파이프로 연결(접속단계)
③ 데이터를 송/수신(송/수신 단계)
④ 파이프를 분리하고 소켓을 말소한다.(연결 끊기 단계)
① 소켓을 만든다.
②-① 소켓을 접속 대기 상태로 만든다(접속 대기 상태 => bind()후 listen() 호출 및 포트번호 지정)
②-② 접속을 접수한다(접속 접수 단계)
③ 데이터를 송/수신(송/수신 단계)
④ 파이프를 분리하고 소켓을 말소한다.(연결 끊기 단계)
Socket을 호출 -> bind 호출 -> 포트번호 지정 -> accept 호출(아직 클라이언트의 접속 패킷이 도착하지 않은 상태) -> 접속 패킷 도착 -> 응답 패킷 반송 -> 접속 접수 동작 실행 -> 접속 대기의 소켓을 복사하여 새로운 소켓 생성(접속 상대의 정보를 비롯한 제어 정보를 새 소켓에 기록)
※ 99소켓을 지정할 때 소켓에 포트만 지정해주는 경우, 서로 다른 클라이언트에게 동일한 포트를 지정해줄 수 없는 문제가 발생한다. 이를 해결하기 위해 소켓을 지정할 때 서버측의 소켓에 할당한 포트 번호뿐만 아니라 클라이언트측의 포트 번호도 사용하고, IP 주소도 추가하여 다음의 네 가지 정보를 사용한다.
① 클라이언트측의 IP주소
② 클라이언트측의 포트 번호
③ 서버측의 IP 주소
④ 서버측의 포트번호
위의 네 가지 정보는 디스크립터 대신 사용할 수 없다. 왜냐하면 소켓을 만든 직후에 아직 접속하지 않은 상태일 때는 네 가지 정보가 준비되어 있지 않기 때문이다. 또한 소켓을 식별할 때 네 가지 정보를 나타내는 것보다 디스크립터라는 한 개의 정보를 나타내는 쪽이 더 간단하다.
(10BASE-T의 경우)
-
LAN 어댑터의 MAC 부분 ① 프리앰블(신호에서 데이터를 구분짓는 클록타이밍을 결정) 추출
② 클록을 같은 간격으로 연장
③ 클록의 위치에서 신호의 변화의 방향 조사
④ 신호의 변화의 방향을 1과 0으로 변형
⑤ 패킷의 맨 마지막에 있는 프레임 체크 시퀀스(FCS)라는 오류 검사용 데이터를 이용하여 오류 유무를 검사
⑥ 오류가 없다면 맨 앞의 MAC 헤더에 있는 수신처 MAC 주소를 조사하여 패킷지 자신을 수신처로 하여 보낸것인지 판단(이더넷의 기본 동작은 먼저 신호를 LAN 전체로 흘리고 해당자만 신호를 수신한다는 방법을 취하기 때문)
⑦ 09디지털 데이터로 되돌린 것을 LAN 어댑터의 내부의 버퍼 메모리에 저장.(여기까지는 LAN 어댑터의 MAC 부분이 실행) -
LAN 드라이버 부분 ① CPU에 인터럽트를 걸어서 LAN 어댑터에서 CPU로 패킷의 도착을 알림.
② CPU는 실행중이던 작업을 중단하고 LAN 드라이버로 실행을 전환
③ LAN 드라이버가 실행되면서 LAN 어댑터의 버퍼 메모리에서 수신한 패킷을 추출
④ 그리고 MAC 헤더의 타입 필드의 값에 따라 프로토콜을 판별하고, 프로토콜을 처리하는 소프트웨어를 호출
① 프로토콜 스택에 패킷이 전달되면 우선 IP 담당 부분이 동작하여 IP 헤더를 점검한다.
② IP 헤더의 내용이 규칙에 따라 올바르게 만들어졌는지부터 점검한 후
③ 수신처 IP 주소가 자신을 대상으로 하는지 조사한다.
④-① 패킷이 자신의 것이라면, 다음에는 조각 나누기에 의해 패킷이 분할되었는지 조사한다.
④-② 만일, 분할되어있는 경우에는 패킷을 일시적으로 메모리에 저장해둔다.
④-③ 그리고 분할된 패킷의 조각이 전부 도착한 시점에서 패킷의 조각을 조립하여 원래 패킷으로 복원한다.
⑤ 패킷 복원이 완료되면 IP 헤더의 프로토콜 번호 항목을 조사하여 해당하는 담당 부분(TCP 또는 UDP)에 패킷을 건네준다.
① 패킷의 TCP헤더에 있는 SYN이라는 컨트롤 비트가 1로 되어있으면 접속 동작의 패킷이다.
② 이 동작이 실행되면 수신처 포트 번호를 조사하여 이 번호와 같은 번호를 할당한 접속 대기 상태의 소켓이 있는지 확인한다. (없으면 오류통지 반송)
③ 해당하는 접속 대기 소켓이 있으면 패킷을 복사하여 새 소켓을 만들고 여기에 송신처의 IP 주소나 포트번호, 시퀀스 번호의 초기값, 윈도우의 값 등 필요한 정보를 기록한다.
④ 동시에 송신버퍼나 수신 버퍼로 사용하는 메모리 영역을 확보한다.
⑤ 그리고 패킷을 받았음을 나타내는 ACK번호, 서버에서 클라이언트에 보내는 데이터에 관한 시퀀스 번호의 초기값, 클라이언트에서 서버로 보내온 데이터를 받기 위한 수신 버퍼의 빈 용량을 나타내는 윈도우 값 등의 항목을 기록한 TCP헤더를 만들고, 이것을 IP 담당 부분에 의뢰하여 클라이언트에 반송한다.
- URI에 서버의 파일 경로와 파일 명으로 파일을 요청할 수 있다.
ex) /home/user2/index.html
- 위와 같이 단순히 URI에 기록되어있는 경로에서 파일을 읽어오면 디스크의 파일에 전부 액세스 할 수 있다는 문제가 있다.
- 웹 서버에서 제공하는 가상의 디렉토리로 파일을 요청한다.
- 웹 서버의 내부에서 실제 내부의 디렉토리와 외부에서 보이는 가상의 디렉토리를 대응시킨다.
-
웹 서버에서 프로그램을 작동시키는 경우 프로그램에서 처리하는 데이터를 HTTP의 리퀘스트 메시지 안에 넣어 브라우저에서 웹 서버로 보내는 것이 일반적입니다.
-
HTTP 리퀘스트 메시지에 데이터를 포함하는 방식
-
method="GET"
-
URI 뒤에 데이터를 포함한다.
-
GET /cgi/sample.cgi?Field1=ABCDEF&SendButton=SEND HTTP/1.1
-
-
method="POST"
-
HTTP 리퀘스트 메시지의 메시지 본문이라는 부분에 데이터를 내장한다.
-
POST /cgi/sample.cgi HTTP/1.1 (몇 행의 헤더 필드) Field1=ABCDEF&SendButton=SEND
-
-
-
웹 서버는 HTTP 리퀘스트의 데이터를 프로그램에 건내준다.
-
웹 서버는 작동시킨 프로그램으로부터 출력 데이터를 받는다.
-
내용이 무엇이든지 데이터를 처리한 결과를 클라이언트에 반송한다.
-
액세스 제어
-
조건에 따라 액세스 동작 여부를 설정하는 기능을 말한다.
-
웹 서버에서 설정하는 조건은 주로 다음의 세 가지이다.
1. 클라이언트의 주소 2. 클라이언트의 도메인명 3. 사용자명과 패스워드
-
-
클라이언트의 주소
-
accept
로 접속을 접수했을 때 클라이언트의 IP 주소를 알 수 있으므로 이것을 점검한다.
-
-
클라이언트의 도메인명
- IP 주소에서 DNS 서버에 도메인 명을 조회한다.
- 이 때, 도메인명을 위조하여 DNS 서버에 등록하는 공격도 가능하므로
- 도메인명에서 IP 주소를 조사하여 송신처 IP 주소와 일치하는지 확인한다.
- 이 방법은 DNS 서버의 조회 메시지가 왕래하는 만큼 시간이 걸린다.
- 응답 시간이 길어진다.
-
사용자명과 패스워드
-
1. 웹 서버가 사용자명과 패스워드를 입력하도록 응답 메시지를 이용해 클라이언트에게 통지 2. 브라우저는 이 응답 메시지를 받으면 사용자명과 패스워드를 입력하는 화면을 표시 3. 사용자가 입력한 위 정보를 리퀘스트 메시지에 기록하고 다시 한 번 서버에 액세스 4. 웹 서버는 통지된 사용자명과 패스워드를 사전에 설정한 것과 대조하여 액세스 가능 여부를 판다. 액세스를 허가하는 경우에는 데이터를 반송
-
- 리퀘스트 메시지에 대해 처리가 완료되면 응답 메시지를 반송한다.
- 웹 서버가 Socket 라이브러리의 write를 호출하여 응답 메시지를 프로토콜 스택에 건내준다.
- 응답 메시지를 어디에 보내야할지 프로토콜 스택에 알려주기 위해 디스크립터를 함께 통지한다.
- 송출된 패킷은 스위치나 라우터를 경유하여 클라이언트에게 도착한다.
- 응답 데이터의 종류를 판단하는 근거는 몇 가지가 있다.
-
Content-Type
-
Content-Type: text/html
- 이 헤더에 따르면 데이터는 html 문서이다.
-
/
의 왼쪽 부분인text
는 주 타입 이라고 한다.- 데이터의 대분류를 나타낸다.
-
/
의 오른쪽 부분인html
은 서브 타입 이라고 한다.- 실제 데이터의 종류를 나타낸다.
- 위의 예시처럼 데이터의 종류가
text
인 경우에는 어떠한 문자 코드를 사용하는지 판단해야 한다.-
charset = utf-8
과 같은 문자 코드의 정보를 부가한다. Content-Type: text/html; charset = utf-8
-
- 이 필드를 사용하여 데이터의 종류를 나타내는 방법은 MIME라는 사양에 규정되어있다.
Multipurpose Internet Mail Extensions
-
-
Content-Encoding
- 데이터의 종류를 조사하고 이 헤더를 조사한다.
- 압축 기술이나 부호화 기술 같이 어떤 변환을 했는지를 이 헤더에 기록한다.
-
- 데이터의 종류에 따라 표시 동작이 달라진다.
- HTML
- 태그의 의미를 해석하여 문장을 배치하면서 화면에 표시한다.
- 실제 화면 표시 동작은 OS가 담당한다.
- 화상 데이터
- HTML의 문장 데이터 안에 화상이 내장되었음을 나타내는 태그를 사용한다.
- 브라우저는 이 태그를 발견하면 화상 데이터의 파일을 서버에서 읽어온다.
- HTML 문서나 화상 데이터 같이 브라우저가 자체에서 표시 기능을 가지고 있는 것은 OS에 지시를 내려 화면에 표시한다.
- 워드프로세서나 프레젠테이션 같은 것은 브라우저가 자체 표시 기능을 가지고있지 않으므로
- 해당 어플리케이션을 호출하여 표시한다.