9 파이프.

Slides:



Advertisements
Similar presentations
Format String Attack! 포맷 스트링 공격 경일대학교 사이버보안학과 학년 남주호.
Advertisements

Linux/UNIX Programming
2장. 프로그램의 기본 구성. 2장. 프로그램의 기본 구성 2-1"Hello, World!" 들여다 보기 /* Hello.c */ #include int main(void) { printf("Hello, World! \n"); return 0;
6 레이스 컨디션.
인공지능실험실 석사 2학기 이희재 TCP/IP Socket Programming… 제 11장 프로세스간 통신 인공지능실험실 석사 2학기 이희재
Department of Computer Engineering
Linux Socket Programming - Introducing Sockets –
Signal & Inter-Process Communication
08. 디바이스 드라이버의 읽기와 쓰기 김진홍
Linux System Programming
Department of Computer Science and Engineering
데이터 파일 C 데이터 파일과 스트림(Stream) 텍스트 파일 처리
6 프로세스 생성과 실행.
6 프로세스 생성과 실행.
Department of Computer Science and Engineering
Inetd Daemon의 이용 VLSI 석사 3학기 고재현.
제15장 파일 입출력 문자열을 출력하는 여러가지 방법 (15-2쪽) 문자열만 처리하는 입출력 함수
Department of Computer Engineering
Department of Computer Engineering
인공지능실험실 석사 2학기 이희재 TCP/IP Socket Programming… 제 7장 소켓 연결의 우아한 종료 인공지능실험실 석사 2학기 이희재
Linux서버를 이용한 채팅프로그램 지도 교수님 : 이형원 교수님 이 름 : 이 은 영 학 번 :
양방향 파이프의 활용 양방향 통신 파이프는 기본적으로 단방향이므로 양방향 통신을 위해서는 파이프를 2개 생성한다.
12장 파이프.
fork로 생성한 자식 프로세스에서 exec 함수군을 호출
레이스 컨디션 컴퓨터공학과 4학년 이교욱.
고급 입출력 함수 School of Electronics and Information. Kyung Hee University.
8장 함수 함수의 필요성 라이브러리 함수와 사용자 정의 함수 함수의 정의, 원형, 호출 배열을 함수 인자로 전달 재귀호출.
링크 파일 생성[1] 링크 하드링크 생성 : link(2) 이미 있는 파일이나 디렉토리에 접근할 수 있는 새로운 이름
Signal & Inter-Process Communication
Department of Computer Engineering
프로세스 생성[1] 프로그램 실행 : system(3) #include <stdlib.h>
컴퓨터 프로그래밍 기초 #02 : printf(), scanf()
파이프와 exec 시스템 호출 (ls | wc)
Homework 6… 12월 2일(금) 11:59pm까지 자신의 이름과 학번을 출력해 주는 유닉스/리눅스 네트워크 소켓 서버 프로그램 과 클라이언트 프로그램 을 작성해 보세요 참고 (실습1) Hello 프로그램 helloserver.c helloclient.c 컴파일.
파일 기술자 복사 파일 기술자 복사 : dup(2) 파일 기술자 복사 : dup2(3)
8 메모리 매핑.
파일 기술자 파일 기술자 현재 열려있는 파일을 구분하는 정수값 저수준 파일 입출력에서 열린 파일을 참조하는데 사용
(ioctl, mmap, fsync&flush)
4장 파일.
메시지 큐[5] – test1.c 메시지 제어: msgctl(2) #include <sys/msg.h>
Department of Computer Engineering
프로젝트 발표 순서 12/7(수), 팀 별 15분 발표순서 PPT (팀 별 이름, 구현 내용, 결과-그래프 포함) 각 기법당
파일 접근권한 제어 stat 구조체의 st_mode 항목에 파일의 종류와 접근권한 정보저장 st_mode 값의 구조.
Department of Computer Engineering
사용자 함수 사용하기 함수 함수 정의 프로그램에서 특정한 기능을 수행하도록 만든 하나의 단위 작업
Signal & Inter-Process Communication
13장 프로세스 사이의 통신.
Linux/UNIX Programming
3장 상수 변수 기본 자료형 키워드와 식별자 상수와 변수 기본 자료형 형변환 자료형의 재정의.
Device Driver 임베디드 시스템 I.
24장. 파일 입출력.
네트워크 프로그래밍의 이해 School of Electronics and Information.
School of Electronics and Information. Kyung Hee University.
Department of Computer Engineering
5장 선택제어문 if 선택문 switch-case 선택문 다양한 프로그램 작성 조건 연산자.
Linux/UNIX Programming
Fflush 사용이유 및 방법 [이유] 키보드에서 입력된 내용은 입력버퍼에 저장되었다가 Enter 키가 들어오면 프로그램으로 전달됨 이 때 입력버퍼에 있는 Enter 키도 프로그램으로 전달됨 그러므로 아래와 같은 프로그램에서 문자 하나를 입력해도 Enter키도 입력된 것으로.
Linux/UNIX Programming
Signal & Inter-Process Communication
Fucntion 요약.
Department of Computer Engineering
4. 셸을 이용한 명령어 입력. Unix 시스템 쉘 간단한 셸 명령 명령 매개변수(Command arguments)
구조체(struct)와 공용체(union)
과제 4: Thread (5월 9일까지) 4장 연습문제 풀이
9 파이프.
Department of Computer Engineering
06. 디바이스의 등록과 해제 김진홍
Signal & Inter-Process Communication
제 29 강 스트링(string) 다루기 s a i s . s T i h t g r i n.
Signal & Inter-Process Communication
Presentation transcript:

9 파이프

학습목표 파이프를 이용한 IPC 기법을 이해한다. 이름 없는 파이프를 이용해 통신프로그램을 작성할 수 있다. 이름 있는 파이프를 이용해 통신프로그램을 작성할 수 있다.

목차 파이프의 개념 이름없는 파이프 만들기 복잡한 파이프 생성 양방향 파이프 활용 이름있는 파이프 만들기

파이프(Pipe) 개요 (1) 파이프(Pipe) 두 프로세스간에 통신할 수 있도록 해주는 특수 파일 일반적으로 “이름없는 파이프(anonymous pipe)”를 의미 이름 없는 파이프는 부모-자식 프로세스 간의 통신에 주로 사용 기본적으로 단방향 통신을 지원 독립적인 프로세스 간의 통신에는 이름있는 파이프(Named Pipe)를 사용

파이프(Pipe) 개요 (2) 간단한 파이프 생성 : 고수준 라이브러리 함수 파이프 생성: popen(3) command : 쉘 명령 mode : “r”(읽기전용 파이프) 또는 “w”(쓰기전용 파이프) fork 함수를 실행하여 자식 프로세스를 생성하고, command에서 지정한 명령을 exec 함수로 실해하여 자식 프로세스가 수행하도록 함. 파이프 생성모드는 부모 프로세스 관점에서 지정 파이프 닫기: pclose(3) 파이프를 닫고, 자식 프로세스들이 종료할 때까지 기다리다가 반환 반환값으로 자식 프로세서의 종료 상태(exit status)을 반환 #include <stdio.h> FILE *popen(const char *command, const char *mode); #include <stdio.h> int pclose(FILE *stream);

[예제 9-1] popen 함수 사용하기(쓰기 전용) ex9_1.c ... 04 int main(void) { 05 FILE *fp; 06 int a; 07 08 fp = popen("wc -l", "w"); 09 if (fp == NULL) { 10 fprintf(stderr, "popen failed\n"); 11 exit(1); 12 } 13 14 for (a = 0; a < 100; a++) 15 fprintf(fp, "test line\n"); 16 17 pclose(fp); 18 19 return 0; 20 } “w”모드로 파이프 생성하고, 자식프로세스는 wc –l 명령 수행 자식 프로세스로 출력 결과는 무엇일까?

[예제 9-2] popen 함수 사용하기(읽기 전용) ex9_2.c ... 04 int main(void) { 05 FILE *fp; 06 char buf[256]; 07 08 fp = popen("date", "r"); 09 if (fp == NULL) { fprintf(stderr, "popen failed\n"); 11 exit(1); 12 } 13 14 if (fgets(buf, sizeof(buf), fp) == NULL) { 15 fprintf(stderr, "No data from pipe!\n"); 16 exit(1); 17 } 18 19 printf("line : %s\n", buf); 20 pclose(fp); 21 22 return 0; 23 } 자식 프로세스는 date 명령 실행 읽기모드로 파이프생성 파이프에서 데이터 읽기 # ex9_2.out line : 2010년 2월 5일 금요일 오후 11시 20분 40초

복잡한 파이프 생성 (1) 파이프 만들기: pipe(2) pipe 함수로 통신과정 파이프로 사용할 파일기술자 2개를 인자로 지정 fildes[0]는 읽기용, fildes[1]은 쓰기용 파일 기술자 pipe 함수로 통신과정 piep 함수를 호출하여 파이프로 사용할 파일기술자 생성 #include <unistd.h> int pipe(int fildes[2]);

복잡한 파이프 생성 (2) pipe 함수로 통신과정 (계속) 2. fork 함수로 자식 프로세스 생성. pipe도 자식 프로세스로 복사됨 3. 통신방향 결정(파이프는 기본적으로 단방향) 파이프를 이용한 통신에서 동기화 문제는?

[예제 9-3] pipe 함수 사용하기(1) ... 06 int main(void) { 07 int fd[2]; ex9_3.c ... 06 int main(void) { 07 int fd[2]; 08 pid_t pid; 09 char buf[257]; int len, status; 11 12 if (pipe(fd) == -1) { 13 perror("pipe"); 14 exit(1); 15 } 16 17 switch (pid = fork()) { 18 case -1 : 19 perror("fork"); 20 exit(1); 21 break; 1. 파이프 생성 2. fork로 자식 프로세스 생성

[예제 9-3] pipe 함수 사용하기(1) 22 case 0 : /* child */ 23 close(fd[1]); ex9_3.c 22 case 0 : /* child */ 23 close(fd[1]); 24 write(1, "Child Process:", 15); 25 len = read(fd[0], buf, 256); 26 write(1, buf, len); 27 close(fd[0]); 28 break; 29 default : 30 close(fd[0]); 31 buf[0] = '\0'; 32 write(fd[1], "Test Message\n", 14); 33 close(fd[1]); 34 waitpid(pid, &status, 0); 35 break; 36 } 37 38 return 0; 39 } C4. 자식 프로세스는 파이프에서 읽을 것이므로 쓰기용 파일기술자(fd[1])를 닫는다. C5. 파이프에서 읽기 P4. 부모 프로세스는 파이프에 쓸 것이므로 읽기용 파일기술자(fd[0])를 닫는다. P5. 파이프에 텍스트를 출력 # ex9_3.out Child Process:Test Message

[예제 9-4] pipe 함수 사용하기(2) ps –ef | grep telnet 동작 구현 ... ex9_4.c ps –ef | grep telnet 동작 구현 ... 06 int main(void) { 07 int fd[2]; 08 pid_t pid; 09 10 if (pipe(fd) == -1) { 11 perror("pipe"); 12 exit(1); 13 } 14 15 switch (pid = fork()) { 16 case -1 : 17 perror("fork"); 18 exit(1); 19 break; 20 case 0 : /* child */ 21 close(fd[1]); 22 if (fd[0] != 0) { 23 dup2(fd[0], 0); 24 close(fd[0]); 25 } 파이프 생성 fd[0]에 0번(표준입력)을 복사 자식프로세스는 파이프 입력으로 0번 사용

[예제 9-4] pipe 함수 사용하기(2) ex9_4.c 26 execlp("grep", "grep", "telnet", (char *)NULL); 27 exit(1); 28 break; 29 default : 30 close(fd[0]); 31 if (fd[1] != 1) { 32 dup2(fd[1], 1); 33 close(fd[1]); 34 } 35 execlp("ps", "ps", "-ef", (char *)NULL); 36 wait(NULL); 37 break; 38 } 39 40 return 0; 41 } grep telnet 명령 실행 fd[1]에 1번(표준출력)을 복사 부모로세스는 파이프 출력으로 1번 사용 ps -ef 명령 실행 # ex9_4.out root 1568 342 0 2ਘ 08 ? 0:00 /usr/sbin/in.telnetd root 1576 342 0 2ਘ 08 ? 0:00 /usr/sbin/in.telnetd root 2763 342 0 2ਘ 10 ? 0:00 /usr/sbin/in.telnetd root 3782 3781 0 09:40:12 pts/3 0:00 grep telnet

양방향 파이프의 활용 양방향 통신 파이프는 기본적으로 단방향이므로 양방향 통신을 위해서는 파이프를 2개 생성한다.

[예제 9-5] 양방향 통신하기 ... 07 int main(void) { 08 int fd1[2], fd2[2]; ex9_5.c ... 07 int main(void) { 08 int fd1[2], fd2[2]; 09 pid_t pid; 10 char buf[257]; 11 int len, status; 12 13 if (pipe(fd1) == -1) { 14 perror("pipe"); 15 exit(1); 16 } 17 18 if (pipe(fd2) == -1) { 19 perror("pipe"); 20 exit(1); 21 } 22 23 switch (pid = fork()) { 24 case -1 : 25 perror("fork"); 26 exit(1); 27 break; 파이프 2개를 생성하기위해 배열2개 선언 파이프 2개 생성

[예제 9-5] 양방향 통신하기 ex9_5.c 28 case 0 : /* child */ 29 close(fd1[1]); 31 write(1, "Child Process:", 15); 32 len = read(fd1[0], buf, 256); 33 write(1, buf, len); 34 35 strcpy(buf, "Good\n"); 36 write(fd2[1], buf, strlen(buf)); 37 break; 38 default : 39 close(fd1[0]); 40 close(fd2[1]); 41 buf[0] = '\0'; 42 write(fd1[1], "Hello\n", 6); 43 44 write(1, "Parent Process:", 15); 45 len = read(fd2[0], buf, 256); 46 write(1, buf, len); 47 waitpid(pid, &status, 0); 48 break; 49 } 50 51 return 0; 52 } 자식 프로세스 fd1[0]으로 읽기 fd2[1]로 쓰기 부모 프로세스 fd1[1]로 쓰기 fd2[0]으로 읽기 # ex9_5.out Child Process:Hello Parent Process:Good

이름 있는 파이프 (1) 이름 있는 파이프 (Named Pipe) 부모-자식간이 아닌 독립적인 프로세스 간에 통신하기 위해서는 이름 있는 파이프 사용 이름 있는 파이프는 FIFO라고도 함 FIFO로 사용할 특수파일을 명령이나 함수로 먼저 생성해야함

이름 있는 파이프 (2) 명령으로 FIFO 파일 생성 mknod 명령 mkfifo명령 mknod 파일명 p # mknod HAN_FIFO p # ls -l HAN_FIFO prw-r--r-- 1 root other 0 2월 13일 12:21 HAN_FIFO # ls -F HAN_FIFO| FIFO 표시 /usr/bin/mkfifo [-m mode] path… # mkfifo -m 0644 BIT_FIFO # ls -l BIT_FIFO prw-r--r-- 1 root other 0 2월 13일 12:28 BIT_FIFO

이름 있는 파이프 (3) 함수로 특수파일 생성 특수파일생성: mknod(2) FIFO 파일 생성: mkfifo(3) mode : 생성할 특수파일의 종류 지정 S_IFIFO : FIFO 특수 파일 S_IFCHAR : 문자장치 특수 파일 S_IFDIR : 디렉토리 S_IFDIR : 블록장치 특수파일 S_IFREG : 일반파일 FIFO 파일 생성: mkfifo(3) mode : 접근권한 지정 #include <sys/stat.h> int mknod(const char *path, mode_t mode, dev_t dev); #include <sys/types.h> #include <sys/stat.h> int mkfifo(const char *path, mode_t mode);

[예제 9-7] FIFO로 데이터 주고 받기 -서버프로그램 ex9_7s.c ... 08 int main(void) { 09 int pd, n; 10 char msg[] = "Hello, FIFO"; 11 12 printf("Server =====\n"); 13 14 if (mkfifo("./HAN-FIFO", 0666) == -1) { 15 perror("mkfifo"); 16 exit(1); 17 } 18 19 if ((pd = open("./HAN-FIFO", O_WRONLY)) == -1) { 20 perror("open"); 21 exit(1); 22 } 23 24 printf("To Client : %s\n", msg); 25 26 n = write(pd, msg, strlen(msg)+1); 27 if (n == -1) { 28 perror("write"); 29 exit(1); 30 } 31 close(pd); 32 33 return 0; 34 } FIFO 파일 생성 FIFO 파일 쓰기모드로 열기 FIFO 파일에 문자열 출력

[예제 9-7] FIFO로 데이터 주고 받기 –클라이언트 프로그램 ... 08 int main(void) { 07 int pd, n; 08 char inmsg[80]; 09 10 if ((pd = open("./HAN-FIFO", O_RDONLY)) == -1) { 11 perror("open"); 12 exit(1); 13 } 14 15 printf("Client =====\n"); 16 write(1, "From Server :", 13); 17 18 while ((n=read(pd, inmsg, 80)) > 0) 19 write(1, inmsg, n); 20 21 if (n == -1) { 22 perror("read"); 23 exit(1); 24 } 25 26 write(1, "\n", 1); 27 close(pd); 28 29 return 0; 30 } ex9_7c.c 서버측에서 생성한 FIFO 파일열기 # ex9_7s.out Server ===== To Client : Hello, FIFO # 서버가 보낸 데이터 읽기 # ex9_7c.out Client ===== From Server :Hello, FIFO #