앞 시간에는 멀리 떨어져 있는 다른 컴퓨터와 데이터를 주고 받는 통신을 하기 위해 소켓을 만들어 주었습니다. 이번에는 그렇게 만든 소켓의 데이터를 바인딩(묶어주기)하고 바인딩된 데이터를 가지고 상대 컴퓨터와 접속하게 하고, 그 접속을 서버(내 컴퓨터)에서 받아들이게 하는 과정까지 다루어 보도록 하겠습니다.
Socket Binding(소켓 바인딩)
통신을 하기 위해서는 통신 기기간(여기서는 컴퓨터) 데이터가 어디에서 오고 어디로 가는지를 알아야 합니다. 이럴 때 사용하는 개념이 아이피(host)주소와 포트(port) 입니다. 그리고 이러한 host와 port를 바인드(묶어주기) 해주어야 어떤 데이터가 오가는지 쉽게 파악할 수 있습니다. 이는 송수신 데이터는 국제 규약인 프로토콜(Protocol)을 따라야 하기 때문입니다. 이에는 가령 신호 송수신의 순서, 데이터의 표현법, 오류 검출법 등이 해당됩니다.
소켓바인더 함수를 정의합니다.▼
서버는 자신의 컴퓨터가 될 것이고, 클라이언트는 타겟(원거리에 있는) 컴퓨터가 될 것입니다. 물론 아이피주소(IP Address)로 개략적인 위치는 가늠할 수 있지만, 해킹을 했다고 하더라도 타겟(클라이언트) 컴퓨터가 어디에 있는지는 알 수 없습니다. 그러므로 가급적 자신의 컴퓨터나 남에게 피해가 가지 않는 선에서 실습을 하시는게 좋습니다. 누군지 모르는 남의 컴퓨터에 무단으로 들락날락하면 유,무형의 제재를 받을 수 있으니 말이죠...;;
사용할 각각의 변수들을 글로벌로 지정합니다.▼
프린트 라인을 넣어 주어서 프리징(freezing)이 일어나고 있지 않다는 것을 확인하게 합니다. 그리고 포트로 지정한 99999는 임의의 숫자입니다. 따라서 출력하기 전에 스트링(String)으로 컨버팅을 해주기 위해 str()을 사용합니다.▼
데이터를 바인딩 하는것은 의외로 간단합니다. 소켓에 펑션(Function) 바인드(bind)를 호출하면 됩니다. 그 안에는 Tuple의 형태로 호스트(host), 포트(port)를 넣어줍니다. 호스트는 보통 IP address 가 됩니다.▼
이제 데이터들은 바인딩이 되었고 listen 할 준비가 되었습니다.
소켓에 펑션(function) listen()을 호출합니다. 인자로는 5가 적당합니다. 여기서 받은 인자 5는 back connection 을 뜻한다. 이 숫자를 넘어서는 connection 은 refusing 하겠다는 의미입니다. 너무 많은 커넥션을 받아들이면 자신의 컴퓨터(서버)에 큰 load가 걸릴 수 있기 때문입니다. 그리고 여기서 listen() 은 서버가 connection을 받아들이게 할 준비를 합니다.
만약 소켓 바인딩이 실패하면, 소켓 바인딩 에러를 출력하게합니다. ▼
그리고 이 이후에 무엇을 할 것인지 보여주게 합니다. 여기서는 다시 바인딩을 시도하게 할 것이므로 "Retrying..." 메시지를 보여주게 합니다. ▼
그런 연후에 socket_bind() 를 호출하여 다시 시도하게 만듭니다.▼
Socket Accept(소켓 받아들이기)
이제 할 일은 누군가가 접속을 해 오면 그 접속을 받아들이게 하는 일입니다.
만약 위에서 listen() 이 없다면, 소켓 accept() 는 작동하지 않습니다. 왜냐하면 Socket Accept이 발생하기 이전에는 반드시 listen() 이 구동되어져야 다음 단계인 accept 가 일어날 수 있기 때문입니다. 가령 문을 안 열었는데, 들어갈 수 없는 것처럼 말이죠. 집이나, 방으로 들어가려면 문을 열어야겠죠? 같은 이치입니다.
이렇게 listen()이 작동하고 있는 중에 socket_accept() 함수가 호출되면 새로운 커넥션(connection)을 수용하게 됩니다.▼
프로그램이 여기까지 아무런 문제없이 잘 진행되고 있는지 확인하기 위해, 우선 몇몇 정보를 프린트 아웃하게 해 보겠습니다.
만약 위의 accept()가 아무런 문제가 없다면, 이 커넥션은 성공한 것입니다. 그래서 다음과 같이 적을 수 있습니다.▼
언제든지 컴퓨터가 연결되면, address 의 첫 번째 인자로는 아이피주소가 할당됩니다. 그리고 두 번째 값은 포트넘버가 할당됩니다. 그래서 언제든지 클라이언트로부터 커넥션이 성립되면, 아이피 주소와, 포트넘버를 알 수 있습니다. address 는 누군가 접속하면, 그 데이터 정보를 알려주고, conn 은 커넥션 주고 받는 대화(conversation) 그 자체입니다.
언제든지 클라이언트로부터 접속이 되면, conn 은 어떤 명령(commands)를 주고 받을지 대기하고 있습니다. 그리고 명령(commands)를 입력 받으면 그대로 실행합니다. 이런 명령을 실행하고 반환되는 그 결과를 우리에게 다시 보내줍니다. 이렇게 보내온 결과를 보고 다시 타겟(클라이언트) 컴퓨터와 명령어를 주고 받으며 간접적으로 통신을 할 수 있게 되는 것입니다. 그래서 이러한 명령어를 포함하겔 될 conn 을 보내는 함수를 다음 시간에 정의해 보도록 하겠습니다.▼
마지막은 통신을 주고 받다가 종료를 하게 되면, conn 을 닫아주어 메모리를 효율적으로 사용할 수 있게 합니다.▼