문제

무엇인지 알아요 dup / dup2 그렇게하지만 언제 사용될 것인지 전혀 모른다.

실용적인 예?

감사.

도움이 되었습니까?

해결책

한 가지 예는 I/O 리디렉션입니다. 이를 위해 어린이 프로세스를 포크하고 stdin 또는 stdout 파일 설명자 (0 및 1)를 닫은 다음 선택한 다른 제출 된 스크립터에서 DUP ()를 수행하여 이제 가장 낮은 파일 설명 자에 매핑됩니다. 사례 0 또는 1.

이것을 사용하면 이제 신청서를 알지 못하는 어린이 프로세스를 실행할 수 있으며 자녀가 STDOUT에 글을 쓸 때마다 (또는 구성된 내용이든 Stdin의 읽기) 데이터가 대신 제공된 제출자에 작성됩니다.

쉘은 이것을 사용하여 파이프로 명령을 구현합니다. /bin/ls | more 한 프로세스의 stdout을 다른 프로세스의 stdin에 연결함으로써.

다른 팁

DUP 및 DUP2를 이해하는 가장 좋은 시나리오는 리디렉션입니다.
가장 먼저 알아야 할 것은 시스템에 입력 및 출력을 처리하는 3 개의 기본 파일 ID (또는 출력 또는 입력 소스를 나타내는 변수)가 있다는 것입니다. 그들은 stdin, stdout, stderr, 정수로 그들은입니다 0,1,2. 대부분의 기능과 같은 기능 fprintf 또는 cout 직접 출력됩니다 stdout.
출력을 리디렉션하려면 예를 들어 한 가지 방법으로 제공됩니다. fprintf 더 많은 인수를 나타내는 기능 in 그리고 out.
그러나 더 우아한 방법이 있습니다. 기본 파일 ID를 덮어 쓰기 위해 출력을 수신하려는 파일을 가리킬 수 있습니다. dup 그리고 dup2 이 상황에서 정확히 일합니다.
한 가지 간단한 예로 시작하겠습니다. 출력을 리디렉션하고 싶다고 가정 해 봅시다 fprintf "ChinaisBetter.txt"라는 TXT 파일에. 우선이 파일을 열어야합니다

int fw=open("chinaisbetter.txt", O_APPEND|O_WRONLY);

그러면 우리는 원합니다 stdout DUP 함수를 사용하여 "ChinaisBetter.txt"를 가리 키려면 :

dup2(fw,1);

이제 STDOUT (1)는 여전히 1이지만 "ChinaisBetter.txt"의 설명자를 가리 킵니다. 그러나 출력은 이제 리디렉션됩니다.
그런 다음 사용할 수 있습니다 printf 일반적으로 결과는 화면에 직접 표시되는 대신 TXT 파일에 있습니다.

printf("Are you kidding me? \n");

추신:

  1. 이것은 직관적 인 설명 만 제공하며 인공 또는 자세한 정보를 확인해야 할 수도 있습니다. 실제로, 우리는 여기서 "복사"라고 말하면 모든 것을 복사하지 않습니다.

  2. 여기의 파일 ID는 파일의 핸들러를 참조합니다. 위에서 언급 한 파일 디스크립터는 레코드 파일의 정보입니다.

POSIX 기능, 특히 스스로 복제하는 것처럼 보이는 기능에 대해 궁금한 점이 있으면 일반적으로 좋습니다. 표준 자체를 확인하십시오. 맨 아래에는 보통 예제가 보일뿐만 아니라 두 가지의 구현 (및 존재)의 추론을 볼 수 있습니다.

이 경우 :

다음 섹션은 유익합니다.

표준 출력을 파일로 리디렉션합니다

다음 예제는 현재 프로세스의 표준 출력을 닫고 표준 출력을 다시 할당하여 참조 된 파일로 이동합니다. pfd, 정리하기 위해 원본 파일 디스크립터를 닫습니다.

#include <unistd.h>
...
int pfd;
...
close(1);
dup(pfd);
close(pfd);
...

오류 메시지 리디렉션

다음 예제는 메시지를 리디렉션합니다 stderr 에게 stdout.

#include <unistd.h>
...
dup2(2, 1); // 2-stderr; 1-stdout
...

응용 프로그램 사용

없음.

이론적 해석

그만큼 dup() 그리고 dup2() 기능은 중복됩니다. 그들의 서비스는 또한 fcntl() 기능. 많은 기존 응용 프로그램이 사용하기 때문에이 책의 IEEE STD 1003.1-2001에 주로이 책에 포함되어 있습니다.

표시된 간단한 코드 세그먼트는 동작이 매우 유사하지만 dup2(),이 부피의 IEEE STD 1003.1-2001에 정의 된 다른 기능에 기초한 준수 구현은 훨씬 더 복잡하다. 가장 명백한 것은 단계와 파일 설명자를 할당하거나 할당하거나 거래 할 수있는 신호-캐리 팅 함수의 가능한 효과가 가장 명백하다. 신호를 차단하여 피할 수 있습니다.

그만큼 dup2() 함수는 유형-유형 버전에서 제공되는 유형-안전 버전의 기능을 제공하기 때문에 불분명하지 않습니다. fcntl(). POSIX ADA 바인딩에 사용됩니다.

그만큼 dup2() 기능은 임계 영역에서 동기화 메커니즘으로 사용하기위한 것이 아닙니다.

EBADF]에 대한 설명에서, 범위를 벗어난 Fildes의 경우는 유효하지 않은 주어진 Fildes의 경우에 포함됩니다. 설명 fildes 그리고 fildes2 관련된 유일한 무효가 있기 때문에 다릅니다. fildes2 범위를 벗어난 지 여부입니다. 즉, 그것은 중요하지 않습니다 fildes2 열린 파일을 참조합니다 dup2() 전화가 이루어집니다.

향후 방향

없음.

또한보십시오

close(), fcntl(), open(), IEEE STD 1003.1-2001의 기본 정의 볼륨, <unistd.h>

역사를 바꾸십시오

1 호에서 처음 출시되었습니다. SVID의 1 호에서 파생되었습니다.

실질적인 예는 출력 메시지를 일부 로그 파일과 같은 다른 스트림으로 리디렉션하는 것입니다. 다음은 I/O 리디렉션을위한 샘플 코드입니다.
원본 게시물을 참조하십시오 여기

#include <stdio.h>

main()
{
    int    fd;
    fpos_t pos;

    printf("stdout, ");

    fflush(stdout);
    fgetpos(stdout, &pos);
    fd = dup(fileno(stdout));
    freopen("stdout.out", "w", stdout);

    f();

    fflush(stdout);
    dup2(fd, fileno(stdout));
    close(fd);
    clearerr(stdout);
    fsetpos(stdout, &pos);        /* for C9X */

    printf("stdout again\n");
}

f()
{
printf("stdout in f()");
}

쉘의 I/O 리디렉션은 DUP2/FCNLT 시스템 호출을 사용하여 구현 될 가능성이 높습니다.

우리는 쉽게 모방 할 수 있습니다 $program 2>&1 > logfile.log dup2 함수를 사용한 리디렉션 유형.

아래 프로그램은 stdout과 stderr .ie를 모두 리디렉션합니다. $program 2>&1 > output DUP2 사용.

#include <stdio.h>
#include <stdlib.h>
#include <unistd.h>
#include <fcntl.h>

int
main(void){
    int close_this_fd;
    dup2(close_this_fd = open("output", O_WRONLY), 1);
    dup2(1,2);
    close(close_this_fd);
    fprintf(stdout, "standard output\n");
    fprintf(stderr, "standard error\n");
    fflush(stdout);
    sleep(100); //sleep to examine the filedes in /proc/pid/fd level.
    return;
}

vagrant@precise64:/vagrant/advC$ ./a.out
^Z
[2]+  Stopped                 ./a.out
vagrant@precise64:/vagrant/advC$ cat output
standard error
standard output
vagrant@precise64:/vagrant/advC$ ll /proc/2761/fd
total 0
dr-x------ 2 vagrant vagrant  0 Jun 20 22:07 ./
dr-xr-xr-x 8 vagrant vagrant  0 Jun 20 22:07 ../
lrwx------ 1 vagrant vagrant 64 Jun 20 22:07 0 -> /dev/pts/0
l-wx------ 1 vagrant vagrant 64 Jun 20 22:07 1 -> /vagrant/advC/output
l-wx------ 1 vagrant vagrant 64 Jun 20 22:07 2 -> /vagrant/advC/output
라이센스 : CC-BY-SA ~와 함께 속성
제휴하지 않습니다 StackOverflow
scroll top