2014년 12월 19일 금요일

TCP/IP 소켓 프로그래밍 11강

도서 추천했다가 다시 11강으로 연결한다.
11강은 프로세스간의 통신법을 알아보자~

11- 1 : 프로세스간 통신의 기본 개념
컴퓨터와 컴퓨터의 통신은 소켓을 통해서 데이터를 주고 받는데
프로세스와 프로세스는 파이프를 통해서 데이터를 주고 받는다.(라임이 맞네?!)

파이프?? 파이프라면 그 어깨 형들이 들고다니는 그 쇠파이프??
맞다 그 파이프다~! 그걸로 빨대 꽂듯이 꽂아서 데이터를 쭉 빨아먹...
미안하다 그게 아니지만 개념은 같다ㅡㅡ;

먼저 파이프를 꽂으려면 파이프를 생성해야 한다.

-파이프 생성 함수-

#include <unistd.h>
int pipe(int filedes[2]);
-filed[0] : 파이프로부터 데이터를 수신하는데 사용되는 파일 디스크립터 저장,(파이프의 출구)
-filed[1] : 파이프로부터 데이터를 전송하는데 사용되는 파일 디스크립터 저장,(파이프의 입구)

위의 함수를 이용하면 프로세스 끼리 통신이 가능해진다.
예제를 보자.
#include <stdio.h>
#include <unistd.h>
#define BUF_SIZE 30

int main(int argc, char *argv[])
{
int fds[2];
//파이프 생성하고 보낼 메세지다
char str[]="Who are you?";
char buf[BUF_SIZE];
pid_t pid;
//파이프 생성
pipe(fds);
//부모 자식 프로세스에 파이프가 생김
pid=fork();
//자식 프로세스에 적용되는 부분
if(pid==0)
{
write(fds[1], str, sizeof(str)); //문자열 보냄
}
else //부모 프로세스에 적용되는 부분
{
read(fds[0], buf, BUF_SIZE); //문자열 받음
puts(buf);
}
return 0;
}

위의 예제를 보면 일방적인 통신이다. 양방향 통신이 가능하게 할 수도 있다.
예제를 보자.
#include <stdio.h>
#include <unistd.h>
#define BUF_SIZE 30

int main(int argc, char *argv[])
{
int fds[2];
//보낼 메세지들이다.
char str1[]="Who are you?";
char str2[]="Thank you for your message";
char buf[BUF_SIZE];
pid_t pid;
//파이프 생성 했다
pipe(fds); 
//자식 프로세서 생성했다.
pid=fork();
//자식 프로세서가 수행할 부분이다. (자식은 0이랑께)
if(pid==0)
{
//부모에게 Who are you?를 날린다.(이런 호로자식...)
write(fds[1], str1, sizeof(str1)); 
sleep(2); //2초 딜레이 한다(이유는 충돌 방지)
//부모에게서 온 메세지를 읽는다.(Thank you for your message)
read(fds[0], buf, BUF_SIZE); 
printf("Child proc output: %s \n",  buf);
}
else //부모 프로세서가 수행할 부분이다.
{
//자식 놈(?)이 Who are you?를 보냈다.
read(fds[0], buf, BUF_SIZE);
//받은 메세지를 출력한다.
printf("Parent proc output: %s \n", buf);
//자식 프로세스에게 Thank you for your message를 보냈다.
write(fds[1], str2, sizeof(str2));
//바로 종료되는 것을 막기 위해 일부러 딜레이 줬다.
sleep(3);
}
return 0;
}

위의 예제와 같이 하나의 파이프로 양방향 통신이 가능하긴 하다.
문제는 위와 같이 언제 메세지가 올지 바로 알수 있는 경우에는 약간의 딜레이로 
수신을 할수는 있지만. 대부분의 경우에는 메세지가 언제 올지 알수 없다.
만약 딜레이를 주석처리하고 실행하면 자식이 보내고 자식이 바로 받아서 읽는다
아이고 의미없다~~
이런 비극을 막기 위해서는 아예 수신 전용, 송신 전용 파이프를 2개 만들어서 하는게 좋다
예제를 보자.

#include <stdio.h>
#include <unistd.h>
#define BUF_SIZE 30

int main(int argc, char *argv[])
{
int fds1[2], fds2[2];
char str1[]="Who are you?";
char str2[]="Thank you for your message";
char buf[BUF_SIZE];
pid_t pid;
//파이프를 2개 생성한다.
pipe(fds1), pipe(fds2);
//자식 프로세스를 생성
pid=fork();
if(pid==0)
{
write(fds1[1], str1, sizeof(str1)); //fds1 파이프를 사용해서 메세지 보낸다.
read(fds2[0], buf, BUF_SIZE);  //fds2 파이프를 사용해서 메세지 받는다.
printf("Child proc output: %s \n",  buf);
}
else
{
read(fds1[0], buf, BUF_SIZE); //fds1파이프를 사용해서 메세지 받는다.
printf("Parent proc output: %s \n", buf); //출력
write(fds2[1], str2, sizeof(str2)); //fds2파이프를 사용래서 메세지 보낸다.
sleep(3);
}
return 0;
}

이번 강은 무지하게 쉬웠다. 파이프 생성해서 서로 통신만 하게 연결만 시키면 된다.
역시 소스를 다운받아서 직접 해보자

12강은 IO 멀티플렉싱을 알아볼 것이다.

댓글 없음:

댓글 쓰기