그물을 뜻하는 Net와 Work의 합성어
분산되어 있는 컴퓨터를 통신망으로 연결한 것
컴퓨터는 하드웨어 / 소프트웨어로 나뉨
소프트웨어는 OS 나 응용 프로그램 등으로 구성되어 있음
이런 네트워크를 이해하기 위해선 프로세스를 이해해야 함
운영체제 역할을 크게 두 가지로 구분하면
1. 하드웨어 자원의 할당
2. 프로세스의 관리
프로세스: 운영체제로부터 자원을 할당 받는 작업의 단위
스레드: 할당 받은 자원을 실제로 이용하는 실행의 단위
프로세스 내에는 여러 스레드가 존재할 수 있다. 프로세스는 완전히 독립된 실행 객체임. 독립되어 있는 만큼 다른 프로세스의 영향을 받지 않지만, 별도의 방법 없이는 서로 통신이 불가능하다.
프로세스간 통신: IPC, 뮤텍스, 세마포어 등 메모리 공유 방법엔 여러가지가 있다.
소켓: 두 개의 프로그램 간 양방향 통신의 하나의 엔드 포인트
소켓은 프로세스와 시스템의 가장 기초적인 부분. 프로세스 간의 통신을 가능하게 한다.
데이터 교환을 위해 양쪽 프로세스에서 임의의 포트를 정하고, 해당 포트간의 연결을 통해 데이터를 주고받는다.
이러한 소켓 통신은 네트워크의 기본이 된다.
서버는 특정 포트가 바인딩된 소켓을 하나 가지고 있다. 이를 통해 listen() 을 하며 클라이언트의 연결을 기다린다.
클라이언트는 서버의 호스트이름과 리스닝하고 있는 포트를 통해 서버와의 연결을 시도한다. 또한 서버에 연결되어 있는 동안 서버에게 자신을 식별시키기 위해 로컬 포트에 바인딩이 된다. 이러한 포트 바인딩 작업은 OS에 의해 이루어진다.
클라이언트가 연결 요청을 하면 서버가 accept()을 한다. 서버는 동일한 로컬 포트에 바인딩된 새로운 소켓을 연다. 예를 들어 80번으로 웹 서버가 listen()을 하고 있으면, 새로운 클라이언트가 연결요청할 때 그 클라이언트와 통신하기 위해 새로운 포트로 소켓을 연다.
웹서버는 80번으로 계속 리스닝을 하고 있어야 하기 때문에 클라이언트와의 연결을 별도의 포트를 통해 바인딩 하는 것이다. 동시에 80번 포트는 지속적으로 연결 요청을 받는데 사용한다.
초창기, 네트워크 장비는 서로 통일이 안 되어 호환이 되지 않았다. 이러한 장비들을 통일시키기 위해 네트워크를 7계층으로 나누어 통일시켰다 (OSI 7계층).
이러한 7계층의 흐름 (어떤 헤더가 붙고 떨어지는지) 등을 이해하는 것이 외우는 것보다 더 중요하다.
HTTP 프로토콜은 HTML과 같은 리소스를 가져올 수 있게 하는 프로토콜이다. 현대 웹에서 이루어지는 모든 데이터 교환의 기초이기도 하고 클라이언트-서버 프로토콜이다.
인터넷에서 클라이언트 서버 간의 연결을 가능하게 하는 통신 규약이 인터넷 프로토콜 스위트 (Internet Protocol Suite) 이다. 이는 인터넷(공용망) 상에서 컴퓨터들이 정보를 주고받는 데 쓰이는 프로토콜의 모음이다.
인터넷 프로토콜 스위트 중에서 TCP/IP가 가장 많이 쓰이므로 TCP/IP 프로토콜 스위트라고 부르기도 한다.
TCP/IP는 패킷 통신 방식의 인터넷 프로토콜인 IP와 전송 조절 프로토콜인 TCP로 이루어져 있다.
IP는 패킷 전달 여부를 보장하지 않는다. 패킷을 보낸 순서와 받는 순서가 다를 수도 있다. 그래서 TCP는 IP 위에서 동작하며 데이터 전달을 보장하고 보낸 순서대로 패킷을 받을 수 있게 하는 시퀀스를 보장하는 역할을 한다.
HTTP/FTP/SMTP 등 TCP를 기반으로 한 많은 어플리케이션 프로토콜이 IP 위에서 동작하므로 TCP/IP라고 부른다.
네트워크는 네트워크 호스트들로 구성이 되어 있다. 이러한 호스트들은 서로 통신이 가능하다. 이러한 통신에 사용하는 프로토콜이 IP이다. IP를 이용한 통신을 하기 위해서, 즉 한 호스트에서 다른 호스트로 패킷을 전달하기 위해서는 호스트의 주소 정보가 필요하다. 주소가 있어야지 패킷을 보낼 목적지를 설정할 수 있기 때문이다. 이런 주소값이 바로 IP Address 이다.
IP Address는 IP 프로토콜을 사용하는 호스트의 주소 정보이다. IP Address가 있어야 패킷이 어느 주소로 갈지 알 수 있다. 예를 들어, 노드들이 직접적으로 연결되어 있지 않은 경우에는 (가장 왼쪽의 노드와 가장 오른쪽의 노드) 다른 노드들을 통해 연결되어 있는 노드들의 정보를 전달해 주어야 한다. 이 경우, 목적지 값이 제대로 설정되어 있어야 해당 호스트에 전달이 가능하다.
IP는 패킷들의 관계 (순서, 전달 보장) 등을 이해하지는 못한다. IP는 목적지를 제대로 찾아가는 것에 중점을 둔 프로토콜이다. 이에 반해 TCP는 통신하고자 하는 양쪽 단말이 준비가 되었는지를 체크하고, 데이터가 제대로 전송되었는지, 변질되지는 않았는지, 수신자가 얼마나 데이터를 받았고 빠진 부분은 없는지를 점검하는 프로토콜이다.
이런 정보는 TCP 헤더에 담겨있고, TCP 헤더는 SYN, ACK, FIN, RESET 등 신뢰성 보장과 흐름 제어, 혼잡 제어에 관여할 수 있는 요소들로 구성되어 있다.
IP 헤더가 TCP 헤더를 제외한, TCP가 실을 수 있는 데이터 크기를 세그먼트라고 부른다.
TCP는 네트워크 장비 간의 논리적 연결을 성립시키기 위해 3 Way Handshake 라는 방법을 사용한다.
3 Way Handshake는 TCP/IP 프로토콜을 사용해서 통신을 할 때 응용프로그램이 데이터를 전송하기 전 정확한 전송을 보장하기 위해 상대방 컴퓨터가 커넥션을 맺을 수 있는 상태인지 체크하고 연결을 수립하는 과정이다.
클라이언트가 서버에 접속을 요청하는 SYN 패킷을 보낸다. 클라이언트는 SYN 패킷을 보내고 SYN, ACK 응답을 기다린다. SYN sent 상태가 된다.
서버가 클라이언트에게 요청을 수락한다는 뜻의 ACK 패킷을 보낸다. 이 때 SYN Flag가 설정된 패킷을 전송하고 다시 ACK 패킷을 받기를 기다린다. 이 때 SYN Received 상태가 된다.
마지막으로 클라이언트가 서버에 ACK을 보내고 이 이후로 연결이 수립되고 데이터를 보낼 수 있는 상태가 된다. 연결 수립 상태가 된다.
3 Way Handshake 방식은 최초로 TCP 연결을 수립할 때 쓰인다. 4 Way Handshake 방식은 연결을 종료할 때 수행된다.
네트워크를 다양한 관점에서 분류할 수 있다. 네트워크를 분류하는 기준은 이용자, 크기 등 다양하다.
서버가 클라이언트와 통신하기 위해서는 IP Address가 필요하다. 인터넷이 보편화되며 IP 주소가 빠르게 고갈되기 시작했다. 지금은 새로운 IPv4 주소의 할당은 중지된 상태이다.
ISP(Internet Service Provider) 회사에서는 일정량의 IP를 보유하고 있고 사용자에게 이를 제공해 준다.
ISP에 인터넷 사용 신청을 하고 공유기를 통해 하나의 공용 IP를 받았다고 가정해 보자. 공유기를 통해 인터넷을 사용하는 다양한 기기들이 있을 것이다. 이러한 공유기가 만들어주는 네트워크를 사설 네트워크라고 한다. 가정 뿐만 아니라 접속할 수 있는 사람이 제한되어 있는 네트워크를 사설 네트워크라고 한다.
사설 네트워크 내에서는 사설 IP가 이용된다. 사설 IP란 인터넷 상에서 사용되는 공용 IP가 아닌 독립된 네트워크 안에서 사용할 수 있는 IP이다.
주소를 가지고 있는 계층은 데이터 링크 계층과 네트워크 계층이다. 2계층은 MAC주소, 3계층은 IP 주소를 사용한다. IP 주소는 32비트 (IPv4), 64비트(IPv6) 이다.
IP 주소는 네트워크 주소와 호스트 주소로 나뉜다. 네트워크 주소는 호스트의 집합이다. 호스트 주소는 하나의 네트워크 내에 존재할 수 있는 호스트를 구분하기 위한 고유의 주소이다.
초기의 IP 주소 체계는 호스트 IP의 갯수에 따라 IP 네트워크의 크기를 다르게 할당할 수 있는 클래스 개념을 도입했었다. (A, B, C, D, E 그거...) 예를 들어 C클래스는 192.0.0.0~223.255.255.0 의 주소를 가지고 있다. 네트워크 주소는 3개의 옥텟, 호스트 주소는 한개의 옥텟이다. 따라서 네트워크 당 256개의 호스트를 가지고 있다. 여기서 네트워크와 브로드캐스트 주소를 빼고 254개의 주소를 사용할 수 있다.
이러한 클래스 기반의 IP 주소 체계는 IP 초창기에는 최적의 선택이었지만 인터넷이 상용화되고 호스트 수가 폭발적으로 증가하며 클래스 기반의 주소 체계는 증가하는 수요를 감당하기에는 부족했다. 또한 IPv4의 가장 큰 문제점은 IP 주소를 낭비하고 있다는 점이다. 예를 들어 A클래스의 경우 1677만 개의 주소를 가지게 되는데 일반적인 기업들이 모두 소비하기에는 너무 큰 숫자이다.
이러한 상황을 해결하기 위해 나온 것이 CIDR(Classless Inter-Domain Routing) 이다. CIDR는 기존의 클래스 체계보다 더 유연하다.
CIDR는 슬래시 뒤의 숫자가 네트워크 주소를 의미한다. 즉 /16 이라면 32비트중 16비트를 네트워크 주소로 사용하겠다는 의미이다. 그 뒤의 16비트를 호스트 주소로 사용한다. 그리고 네트워크에서 첫번째 주소와 마지막 주 (192.168.x.x 라면 192.168.0.0 / 192.168.255.255) 는 네트워크 주소와 브로드캐스트 주소이므로 65534개의 IP를 사용할 수 있다. 클라우드라면 추가적으로 DNS나 관리의 용도로 일반적으로 3개의 IP가 더 예약 되어있다.
현대는 단일 네트워크 대역이 아닌 인터넷을 통한 광범위 대역의 네트워크를 기반으로 리소스를 사용하고 있다. 이 때 나오는 개념이 LAN, WAN 등의 개념이다.
허브로 묶여있는 PC들, 스위치로 묶여있는 PC들의 집합을 일반적으로 세그먼트라고 부른다. 세그먼트 범위 내의 컴퓨터들은 패킷을 교환할 필요 없이 직접 데이터를 송수신할 수 있다. 이 케이블 분배기의 역할을 하는 것이 허브와 스위치다. 허브와 스위치는 LAN 수준에서 사용한다. 외부 네트워크와 통신을 하게 되려면 IP가 필요하다. 허브와 스위치는 MAC 주소를 읽을 수 있을 뿐, IP 주소를 읽지를 못한다.
따라서 외부 네트워크, 즉 인터넷이 형성되려면 라우터가 필요하다. 라우터는 IP주소를 바탕으로 한 네트워크에서 다른 네트워크로 데이터를 라우팅하거나 전달할 때 사용하는 장치다. 라우터로 데이터 패킷이 수신되면 첫 번째로 자신이 갖고 있는 네트워크 용인지, 외부 네트워크 용인지를 판단하여 IP 주소를 검사한다.
전자의 경우에는 받고 후자의 경우에는 다른 라우터로 트래픽을 보낸다. 이처럼 라우터 간의 패킷 교환이 이루어지며 네트워크 대역이 점점 확장된다.
인터넷 상의 클라이언트와 서버의 통신을 위해서는 각자의 고유한 IP 주소가 있어야 한다. 사설 네트워크는 인터넷과 독립적인 네트워크이다. 내부 장비는 사설 IP를 가지게 된다. 이러한 사설 IP로는 통신이 불가능하다.
이런 상황에서 사용되는 기술이 NAT 이다. 네트워크 주소인 IP를 변환한다는 뜻이다. NAT는 IPv4의 주소부족 문제를 해결하기 위한 방법으로 디자인되었다. 사설 네트워크 주소를 사용하는 망에서 외부 공인망과 통신하기 위해 네트워크 주소를 변환해 준다.
사설 IP의 사용자는 공용 인터넷 망을 통해 서버와 통신하기 위해서 공용 IP가 필요하다. 사용자의 트래픽이 NAT 디바이스를 거치게 될 때 NAT 디바이스의 공용 IP로 변환된다. 이런 NAT 디바이스의 공용 IP를 가지고 인터넷에 있는 서버와 통신한다.
클라우드 네트워크는 백본이 연결되어 있는데, 그 내에서 VPC 역할을 만들게 되면 VPC는 사용자 네트워크 안에서 격리된 네트워크 공간이다. 즉, 사설 네트워크이다. 이런 VPC에서 공용망 통신을 하려면 보통 NAT 게이트웨이를 통해 변환되어 나간다.
NAT는 Source를 바꾸는 SNAT와 Destination을 바꾸는 DNAT 두 종류가 있다. 일반적으로는 연결이 stateful 하므로 (방화벽이나 라우터가 연결 상태를 추적하여, 이로 인해 이슈가 발생하지 않도록 한다.) egress traffic이 변환이 되면 ingress traffic은 자동으로 처리되므로 DNAT는 어색할수도 있다.
호스트의 도메인 이름을 호스트의 네트워크 주소로 바꾸거나 그 반대의 변환을 수행한다. 특정 컴퓨터의 주소를 찾거나 임의의 장치의 주소를 찾기 위해 사람이 이해하기 쉬운 도메인 이름을 IP 주소로 변환한다.
주 컴퓨터의 도메인 이름을 IP 주소로 변환하고 라우팅 정보를 제공하는 분산형 데이터베이스 시스템이다.
인터넷은 두 개의 주요 이름 공간을 관리한다. 하나는 도메인 네임 계층, 하나는 IP 주소 공간이다. 도메인 네임 시스템은 도메인 네임 계층을 관리하고 해당 네임 계층과 주소 공간간의 변환 서비스를 제공한다.
인터넷 네임 서버와 통신 프로토콜은 DNS의 네임 시스템을 구현하고 DNS 네임 서버는 도메인을 위한 DNS 레코드를 저장하는 서버이다. DNS는 데이터베이스에 대한 쿼리 응답 정보를 리턴해준다.
사용자가 웹 브라우저에 주소를 입력하고 전송하면, 요청은 일반적으로는 가장 첫 번째로 케이블 인터넷 공급 업체, 광대역 공급 업체 혹은 기업 네트워크와 같은 인터넷 서비스 공급 업체가 관리하는 DNS 해석기로 라우팅된다.
보통 DNS 서버는 OS에 등록되어 있는 곳을 가리키는데 이 DNS 서버를 가기 전에 ISP에서 제공하는 서버를 탄다. 이 ISP에 등록되어 있는 도메인 해석기가 요청을 DNS Root name server로 보낸다. www.example.com
의 경우 .com으로 끝나므로 .com TLD 서버로 리턴한다.
.com TLD Name Server에서 네임 서버를 알려주고, 해당 네임 서버에서 실제 서버를 호스팅하고 있는 네임 서버를 찾아 IP주소를 리턴한다. 이 리턴된 IP 주소는 DNS resolver를 통해 전달되고 TCP/IP 연결을 수행한다.
이러한 과정을 매 연결마다 수행하지 않는다. 일반적으로는 브라우저 레벨에서 관리되는 DNS 캐시가 있다.
HTTPS는 HTTP의 보안이 강화된 버전이다. HTTPS는 넷스케이프 웹 프로토콜이다. 거의 모든 웹 서비스에서 사용되고 있다. HTTPS는 소켓 통신에서 일반 텍스트를 사용하는 대신 SSL/TLS 등의 프로토콜을 사용해 세션 데이터를 암호화한다.
SSL이 초기 버전이고, SSL이 지원을 중단하자 나온 후속 버전이 TLS이다. 두 가지 모두 인터넷을 통한 안전한 인증과 데이터 전송을 제공한다. SSL와 TLS는 메세지 인증에 차이점이 있다. SSL은 메시지 인증을 위해 MAC을 사용한다. 전송 중에 메시지가 변조되지 않도록 한다. TLS는 보호를 위해 MAC을 사용하지 않고 암호화 알고리즘을 사용해 데이터의 변조를 방지한다.
TLS는 SSL의 직접적인 후속 버전이다. 현재는 SSL은 더 이상 사용되지 않고 TLS를 사용한다. 따라서 SSL 인증서는 지금은 TLS 동작 원리이다.
TLS는 대칭키 암호화 방식과 공개키 암호화 방식을 두 가지 모두 사용한다.
대칭키: 암복화에 사용하는 키가 동일하다. 해당 키가 아는 사람은 모두 문서를 복호화할 수 있다. 대표적인 알고리즘은 DES, 3DES, AES, SEED, ARIA 등이 있다. 공개키 암호화 방식에 비해 연산 속도가 빠르지만 키를 교환해야 하는 문제와 키를 교환하는 방법이 필요하다. 사용자마다 각각의 키가 필요하므로 관리해야 할 키가 많다.
공개키: 대칭키 암호화 방식보다 복잡한 연산을 거친다. 대표적인 알고리즘은 RSA, DSA, ECC가 있다. 대칭키 방식의 문제점을 해결하기 위해 만들어졌다. 공개키 방식의 키는 공개되어 있다. 따라서 키를 교환할 필요가 없어진다. 공개키는 모든 사람이 접근 가능한 키이고, 개인키는 각 사용자만이 가지고 있는 키가 된다.
수신자가 공개키와 개인키 페어를 만든다. 송신자가 접근 가능한 환경에 수신자의 공개키를 공개한다. 수신자의 개인키는 수신자만이 가지고 있다. 송신자는 수신자의 공개키를 받아 보낼 데이터를 수신자의 공개키로 암호화한다. 암호화된 데이터를 수신자에게 보낸다. 수신자는 암호화된 데이터를 자신이 가지고 있던 개인키로 복호화한다.
공개키 방식은 키가 공개되어 있으므로 따로 키교환이나 분배를 할 필요가 없다. 중간공격자가 개인키를 가지고 있다 해도 수신자만이 암호화한 데이터를 복호화할 수 있으므로 인증을 할 수 있는 환경을 제공한다.
인증서는 이러한 공개키 기반이다.
HTTPS에서 공개키로 사용되는 것이 인증서이다. 인증서에는 키나 소유자에 대한 정보, 인증사 발급자의 디지털 사인 등이 포함되어 있다. 루트 인증서는 최상위 기관인 루트 인증 기관에서 발급된 인증서를 뜻한다. TLS 루트 인증서는 기관에서 직접 발급한 인증서이다. 다른 인증서와는 달리 루트 인증서는 발급 기관에서 자체 서명을 하게 된다. 루트 인증서의 개인키는 TLS 인증서 계층 구조의 다른 인증서의 서명을 하는데 사용된다.
이러한 루트 인증서는 매우 엄격하게 발급되므로 보통 OS나 브라우저에 이미 설치되어 있다. 일반적으로 공개가 되어 있고 다른 루트 인증서를 사용하고자 하는 경우에는 브라우저나 OS에 등록하면 된다.
루트 인증서를 보호하기 위해 중간 인증서를 두는 경우가 많다. 실제 서비스를 제공하는 웹서버들은 루트 인증서가 아닌 중간 기관을 통해 인증서를 발급하는 경우가 많다.
TLS 인증서는 인증서를 발급한 기관의 정보, 서비스를 제공하는 도메인 등의 정보, 즉 서버의 공개키가 포함되어 있다. 이 내용은 인증 기관에 의해 암호화된다. 이 때 공개키 암호화 기법이 사용된다. 이 때는 특이하게 인증 기관의 개인키로 암호화가 진행된다.
브라우저에는 인증기관의 공개키가 깔려있으므로 공개키에 의해 복호화가 가능해진다. 이 서버를 보증하는 것을 인증 회사가 갖고 있는 개인키로 암호화하면 브라우저에 깔려 있는 공개키를 통해 해당 인증 기관에서 만들어진 인증서가 맞다는 것을 인정한다. 이것이 HTTPS 인증서의 핵심이다.
즉, 브라우저가 보유하고 있는 인증 기관의 공개키로 복호화가 가능하다는 것은 해당 공개키와 쌍을 이루는 개인키로 암호화되었다는 것을 보증하는 것이다. 해당 데이터가 인증 기관으로 왔음이 증명되는 것이다.
클라이언트가 공개키를 가지고 보안성 검증이 완료되면 사이트를 신뢰할 수 있으므로 해당 공개키를 활용해 서버와 소통하며 대칭키인 세션키를 가지고 소통할 수 있게 된다.
인증 기관의 비공개키로 암호화된 인증서가 브라우저가 가지고 있는 공개키로 복호화를 진행하면 공개키를 활용하여 세션키를 만든다. 이 세션키를 통해 통신을 시작한다. 이러한 HTTPS 연결을 하는 과정을 TLS Handshake 라고 한다.
클라이언트가 서버에게 hello를 보내며 handshake를 시작한다. 여기서 사용하고자 하는 TLS의 버전, 암호 제품군 등의 내용을 실어 보낸다.
hello 메시지를 받은 서버는 서버가 가지고 있는 서버의 TLS 인증서, 서버에서 사용하는 암호 제품군 (알고리즘) 을 보낸다.
클라이언트는 인증기관을 통해 서버 인증서를 검증한다. 확인이 완료되면 랜덤한 시퀀스를 서버의 공개키로 암호화하고 보낸다.
여기서 서버가 클라이언트에게 인증서를 요구한다면 서버 인증서와 같은 방식으로 암호화를 해 전송한다. 서버가 클라이언트로부터 서버의 공개키로 받은 문자열을 자신의 개인키로 해독한다.
클라이언트가 아까 보낸 암호화된 시퀀스를 대칭키로 활용할 세션키로 만든다. 그 후 finish를 서버에 보낸다.
서버가 클라이언트가 보낸 랜덤 시퀀스를 개인키로 복호화하고 그 동일한 랜덤 문자열을 세션키로 만든다. 그러면 대칭키가 되므로 똑같이 finish를 보내 연결을 수립하고 HTTPS 통신을 수행한다.
이러한 HTTPS 통신은 엔드포인트 단에서 수행하고, 내부에서의 통신은 offloading 시키고 HTTP로 수행하는 경우가 많다 (지만 사실은 다 HTTPS 를 써야 하는 것이 맞긴하다)...