2011-07-24 16 views
6

Próbuję użyć przekierowań w C, aby przekierować dane wejściowe do jednego pliku, a następnie ustawić standardowe wyjście z powrotem do drukowania na ekranie. Czy ktoś mógłby mi powiedzieć, co jest nie tak z tym kodem?Przekierowywanie standardowego wyjścia c, a następnie resetowanie standardowego wyjścia

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

int main(int argc, char** argv) { 
    //create file "test" if it doesn't exist and open for writing setting permissions to 777 
    int file = open("test", O_CREAT | O_WRONLY, 0777); 
    //create another file handle for output 
    int current_out = dup(1); 

    printf("this will be printed to the screen\n"); 

    if(dup2(file, 1) < 0) { 
     fprintf(stderr, "couldn't redirect output\n"); 
     return 1; 
    } 

    printf("this will be printed to the file\n"); 

    if(dup2(current_out, file) < 0) { 
     fprintf(stderr, "couldn't reset output\n"); 
     return 1; 
    } 

    printf("and this will be printed to the screen again\n"); 

    return 0; 
} 
+1

Istnieje zupełnie inny sposób rozwiązania tego samego problemu tutaj: http://stackoverflow.com/questions/584868/rerouting-stdin-and-stdout-from-c. – Sam

Odpowiedz

3

Twój drugi dup2 połączenie jest źle, wymienić:

if (dup2(current_out, 1) < 0) { 
4

Jedno musisz upewnić się zrobić wcześniej, że będzie działać w ogóle, to zadzwonić fflush(stdout); przed włączeniem deskryptor stdout pliku spod niego. Prawdopodobnie dzieje się tak, że biblioteka standardowa C buforuje twoje dane wyjściowe, nie zdając sobie sprawy, że przesuwasz się pod deskryptorami plików pod nią. Dane, które piszesz przy użyciu printf(), nie są wysyłane do podstawowego deskryptora pliku, dopóki jego bufor nie zapełni się (lub Twój program powróci z main).

Włóż rozmowę tak:

fflush(stdout); 
    if(dup2(file, 1) < 0) { 

zarówno przed wywołań dup2().

+0

Nie sądzę, że był to problem OP, ale jest to bardzo dobra rada i prawie zawsze należy go stosować za każdym razem, gdy miksujesz stdio z deskryptorem pliku io. –

+1

To prawda, właściwie nie zauważyłem początkowo niepoprawnego deskryptora pliku, dopóki ktoś o tym nie wspomniał. Podczas zapisu na terminal, wyjście stdio będzie prawdopodobnie buforowane liniowo, więc kod bez 'fflush()' prawdopodobnie zadziała, dopóki OP nie spróbuje przekierować stdout do pliku. –

1

Wystarczy zastąpić dup2(current_out, file) z dup2(current_out, 1) i wszystko powinno działać lepiej.

Powiązane problemy