无法在C中创建shell(Seg-Fault和ferror)

我一直在关注如何制作自己的shell的教程,但我已经被困了几天了。

两件事情:

  1. 编译和运行此代码时,它将随机出现分段错误,我无法弄清楚原因。
  2. if语句`if(ferror!= 0)`似乎总是如此。 这很奇怪,因为我不明白为什么fgets()main()函数中失败了。

有关这些主题的任何信息(或有关创建此shell的其他主题)将不胜感激。

#include  #include  #include  #include  #define MAXSIZE 512 int parseCmd(char *cmd, char *args[]) { printf("LOGGER: parseCmd(cmd=%s, args=%p)\n", cmd, args); char cmdDelims[] = {' ','>'}; char *cmdReader; cmdReader = strtok(cmd, cmdDelims); int i = 0; while (cmdReader != NULL) { args[i] = strdup(cmdReader); printf("LOGGER: args[%d]=%s\n", i, args[i]); cmdReader = strtok(NULL, cmdDelims); i++; } return 0; } void printToLine(char *args[]) { int length; length = sizeof(args) / sizeof(char); int i = 0; while (i "); // get input from command line fgets(in, MAXSIZE, stdin); if (ferror != 0) { perror(error_message); } // get pointer to command line input w/o the newline cmd = strtok(in, inDelims); // parse the command into separate arguments errorBit = parseCmd(cmd, args); if (errorBit) { perror(error_message); exit(1); } printToLine(args); // check if the user wants to exit the shell if (strcmp(*args, "exit") == 0) { terminationBit = 0; } } return 0; } 

以下是一些输出:

 **[ray@12] (6)$ mysh** mysh>1 2 3 An error has occurred : Success LOGGER: parseCmd(cmd=1 2 3, args=0x7fff4a50b080) LOGGER: args[0]=1 LOGGER: args[1]=2 LOGGER: args[2]=3 1 2 3 Segmentation fault (core dumped) **[ray@12] (7)$ mysh** mysh>1 2 3 4 5 6 7 8 9 10 An error has occurred : Success LOGGER: parseCmd(cmd=1 2 3 4 5 6 7 8 9 10, args=0x7fffba053d70) LOGGER: args[0]=1 LOGGER: args[1]=2 LOGGER: args[2]=3 LOGGER: args[3]=4 LOGGER: args[4]=5 LOGGER: args[5]=6 LOGGER: args[6]=7 LOGGER: args[7]=8 LOGGER: args[8]=9 LOGGER: args[9]=10 1 2 3 4 5 6 7 8 mysh>1 2 3 An error has occurred : Success LOGGER: parseCmd(cmd=1 2 3, args=0x7fffba053d70) LOGGER: args[0]=1 LOGGER: args[1]=2 LOGGER: args[2]=3 1 2 3 4 5 6 7 8 

对于ferror错误,你需要测试ferror(stdin) ,而不是ferror 。 后者是函数地址,永远不会为零:

 if (ferror(stdin) != 0) { perror(error_message); } 

对于至少一些段错误,这不符合你的想法:

 length = sizeof(args) / sizeof(char); 

这将告诉您用于存储指针的字节数,取决于4或8,而不是参数的数量。

因此,如果您有四个(或八个)参数,它似乎会起作用。 如果你有更多,它似乎会忽略一些参数。 如果你的数量较少,它将从Void中获取缺少的参数,从而导致(几乎可以肯定的)分段错误。

您需要独立计算length并传递它,或者将一些终结符存储在args ,例如在找到的最后一个有效参数后添加NULL参数:

  cmdReader = strtok(NULL, cmdDelims); i++; } args[i] = NULL; return 0; } void printToLine(char *args[]) { int i = 0; while (args[i]) { printf("%s\n", args[i]); i++; } }