这个基本shell程序有什么问题?它会在前几个命令中正常运行,但结果总是以段错误结束

时间:2014-01-27 20:52:42

标签: c linux shell lex

我必须使用lex和c代码构建一个简单的shell程序。 lex部分用于分解输入。它是为我提供的,我不应该改变它。我正在让我的代码运行像“ls”这样的基本命令。它似乎在我运行命令的前几次工作,但最终总是出现故障。这是提供的lex代码:

%{
int _numargs = 10;
char *_args[10];
int _argcount = 0;
%}

WORD [a-zA-Z0-9\/\.-]+
SPECIAL [()><|&;*]

%%
_argcount=0; 
_args[0]=NULL; 

{WORD}|{SPECIAL} { 
if(_argcount < _numargs-1) {
_args[_argcount++]= (char *)strdup(yytext);
_args[_argcount]= NULL;
}
}

\n return (int)_args;

[ \t]+

.

%%

char **getln() {
return (char **)yylex();
}

这是C代码:

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

extern char **getln();

int main() {
    int i;
    char **args; 
    int child1;
    int status1;
    int counter=0;
    int argCount = 1;

    char **array = (char **)malloc(1500 * sizeof(char *));
    for (i = 0; i < 1500; ++i) {
        array[i] = (char *)malloc(500);
    }
    strcpy(array[0],"ls\0");
    array[1] = NULL;

    while(1) {
        args = getln();
        printf("is error here?");
        strcpy(array[0], args[counter]);

        for(i = (counter+1); args[i] != NULL; i++) {
            printf("\nRight before copying to subarray");
            strcpy(array[argCount], args[i]);
            argCount++;
        }

        array[argCount] = NULL;

        if (strcmp(args[counter],"exit")==0) exit(0);

        child1 = fork();
        if(child1==0){

            execvp(array[0], array);
            printf("Unknown command, please try again.");
            exit(1);
        }
        else{
            while (wait(&status1) != child1);
        }

        for(i = 0; args[i] != NULL; i++) {
            printf("Argument %d: %s\n argCount: %d", i, args[i], argCount);
        }
        argCount = 1;
        counter++;
    }
} 

提前感谢任何建议。如果有一些简单的方法可以调整getln()函数来在每次调用时覆盖args数组,这可能比我正在尝试的更容易,但我不知道如何去做。

1 个答案:

答案 0 :(得分:0)

好像你已经把

_argcount=0;
_args[0]=NULL;

在规则部分的顶部,希望这些语句将在yylex()的开头执行。而且你已经注意到它们没有被执行(它会一直追加到以前的值,因为_argcount永远不会回到0)。

显而易见的事情就是在getln()之前将这些陈述移至yylex()

你现在拥有的词法分析器将忽略输入中的字符串_argcount=0;,因为它将匹配该模式,并且没有任何动作可以使用它。第二行甚至更冷,因为[0]是一个字符类。它使词法分析器忽略字符串_args0=NULL;