c - UNIX shell I/O 重定向

标签 c linux

<分区>

我正尝试在 C 中实现 LINUX shell,但是当我尝试运行这样的命令时:sort -u < in.txt > out.txt它说:sort: cannot read: '<': No such file or directory .我还尝试了其他命令,如 ls -l > out.txt等等,但它一直告诉我同样的事情。这是我的代码:

#include <string.h>
#include <unistd.h>
#include <stdlib.h>
#include <sys/wait.h>
#include <fcntl.h>
#include <sys/types.h>


#define LENGTH 1024

int main(){
char line[LENGTH];
char* argv[100];
char* path= "/bin/";
char fullPath[30];
int option;
char* inputFile;
char* outputFile;   

while(1){

    printf("mysh3>");

    if(!fgets(line,LENGTH,stdin)){
        break;
    }

    size_t length = strlen(line);
    if(line[length-1]=='\n')
        line[length-1] = '\0';

}

char* token; 
token = strtok(line," ");
int i = 0;
while(token!=NULL){
    argv[i]=token;
    token = strtok(NULL," ");
    i++;
}

if(argv[1]==">"){
    option=1;
    outputFile=argv[2];
}
else if(argv[2]==">"){
    option = 1;
    outputFile=argv[3];
}
else if(argv[1]=="<" && argv[3]==">"){
    option=2;
    inputFile=argv[2];
    outputFile=argv[4];
}
else if(argv[2]=="<" && argv[4]==">"){
    option=2;
    inputFile=argv[3];
    outputFile=argv[5];
}
else if(argv[1]=="<" && argv[3]==">>"){
    option=3;
    inputFile=argv[2];
    outputFile=argv[4];
}
else if(argv[2]=="<" && argv[4]==">>"){
    option=3;
    inputFile=argv[3];
    outputFile=argv[5];
}


argv[i]=NULL;

strcpy(fullPath, path);
strcat(fullPath, argv[0]);

for(int i = 0; i < strlen(fullPath); i++){  
    if(fullPath[i]=='\n'){
        fullPath[i]='\0';
    }
}

int ret=forkEx2(argv,inputFile,outputFile,fullPath,option);
if(ret==-1) {
    return -1;
}

int forkEx2(char* argv[],char* inputFile,char* outputFile,char 
fullPath[],int option){
int fd;
pid_t pid,waitPid;
pid = fork();
if(pid<0){
    perror("ERROR: Fork failed.\n");
    return -1;
}
else if(pid==0){
    if(option==1){
        fd=open(outputFile,O_CREAT | O_TRUNC |  O_WRONLY, 0600);  //if the file does not exist the system create it. Clear all data from the file. Open the file for write only.Store its file descriptor in fd

        dup2(fd,STDOUT_FILENO);  //replace the standar out with the file
        close(fd);
    }
    else if(option==2){
        fd=open(inputFile,O_RDONLY,0600);  //open the file for read only

        dup2(fd,STDIN_FILENO);  //replace the standar in with the file
        close(fd);

        fd=open(outputFile,O_CREAT | O_TRUNC |  O_WRONLY, 0600);  //if the file does not exist the system create it. Clear all data from the file. Open the file for write only

        dup2(fd,STDOUT_FILENO);  //replace the standar out with the file
        close(fd);
    }
    else if(option==3){
        fd=open(inputFile,O_RDONLY,0600);  //open the file for read only

        dup2(fd,STDIN_FILENO);  //replace the standar in with the file
        close(fd);

        fd=open(outputFile, O_APPEND | O_WRONLY, 0600);  //append at the end of the file. Open the file for write only

        dup2(fd,STDOUT_FILENO);  //replace the standar out with the file
        close(fd);
    }

    execvp(fullPath,argv);
    perror("ERROR: Child should never arrive here.\n");

}

else{
    waitPid = wait(&waitPid);
    if (waitPid == -1) {
        perror("ERROR: Waitpid failed.\n");
        return -1;
    }

    printf("Parent: Finished pid %d.\n", waitPid);
}
}                   

}

感谢任何帮助。

最佳答案

让我们以这种情况为例(在所有情况下都是一样的):

else if(argv[2]=="<" && argv[4]==">"){
    option=2;
    inputFile=argv[3];
    outputFile=argv[5];
}

首先,您使用 == 比较字符串:这是行不通的。您必须使用 strcmp 或比较指针。

然后,您可以正常提取输入文件和输出文件,但您忘记从 argv 中删除重定向参数。您必须过滤掉它们(每次遇到一个重定向参数时,通过移动参数数组的其余部分)

此外:您应该初始化您的 argv 数组,否则如果没有足够的参数,您可能会遇到未定义的行为。

关于c - UNIX shell I/O 重定向,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/43397140/

相关文章:

linux - 无法使 crontab 工作

c# - C dll向C#返回多个变量

无法命名具有指定优化的可执行文件

c - 如何知道变量是否是 C 中的函数指针?

linux - 有关远程主机标识更改的重定向警告

linux - 在局域网中配置 LAMP 网络服务器

c - 如何使用 MinGW 在 Windows 上使用 OpenSSL 编译程序

c - malloc 可以分配的最大内存

c++ - devIL .so 在 ubuntu 上我把它们放在哪里 - 运行时错误

linux - AWK 对 2 列的值求和并附加到记录