gpt4 book ai didi

c - 帮助简单的 linux shell 实现

转载 作者:塔克拉玛干 更新时间:2023-11-02 23:42:48 25 4
gpt4 key购买 nike

我正在用 c 实现一个简单版本的 linux shell。

我已经成功地编写了解析器,但是我在派生子进程时遇到了一些问题。但是,我认为问题出在数组、指针等方面,因为这个项目刚开始使用 C,对它们还不是很了解。

我遇到了段错误,但不知道从哪里来的。非常感谢任何帮助。

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

#define MAX_COMMAND_LENGTH 250
#define MAX_ARG_LENGTH 250

typedef enum {false, true} bool;

typedef struct {
char **arg;
char *infile;
char *outfile;
int background;
} Command_Info;

int parse_cmd(char *cmd_line, Command_Info *cmd_info)
{
char *arg;
char *args[MAX_ARG_LENGTH];

int i = 0;
arg = strtok(cmd_line, " ");
while (arg != NULL) {
args[i] = arg;
arg = strtok(NULL, " ");
i++;
}

int num_elems = i;
if (num_elems == 0)
return -1;

cmd_info->infile = NULL;
cmd_info->outfile = NULL;
cmd_info->background = 0;

int iarg = 0;
for (i = 0; i < num_elems-1; i++)
{
if (!strcmp(args[i], "<"))
{
if (args[i+1] != NULL)
cmd_info->infile = args[++i];
else
return -1;
}

else if (!strcmp(args[i], ">"))
{
if (args[i+1] != NULL)
cmd_info->outfile = args[++i];
else
return -1;
}

else
cmd_info->arg[iarg++] = args[i];
}

if (!strcmp(args[i], "&"))
cmd_info->background = true;
else
cmd_info->arg[iarg++] = args[i];

cmd_info->arg[iarg] = NULL;

return 0;
}


void print_cmd(Command_Info *cmd_info)
{
int i;
for (i = 0; cmd_info->arg[i] != NULL; i++)
printf("arg[%d]=\"%s\"\n", i, cmd_info->arg[i]);
printf("arg[%d]=\"%s\"\n", i, cmd_info->arg[i]);
printf("infile=\"%s\"\n", cmd_info->infile);
printf("outfile=\"%s\"\n", cmd_info->outfile);
printf("background=\"%d\"\n", cmd_info->background);
}

void get_cmd(char* str)
{
fgets(str, MAX_COMMAND_LENGTH, stdin);
str[strlen(str)-1] = '\0'; //apaga o '\n' do fim
}

pid_t exec_simple(Command_Info *cmd_info)

{
pid_t pid = fork();


if (pid < 0)
{
perror("Fork Error");
return -1;
}



if (pid == 0)

{
execvp(cmd_info->arg[0], cmd_info->arg);

perror(cmd_info->arg[0]);
exit(1);
}


return pid;

}

int main(int argc, char* argv[])
{

while (true)
{
char cmd_line[MAX_COMMAND_LENGTH];
Command_Info cmd_info;

printf(">>> ");

get_cmd(cmd_line);

if ( (parse_cmd(cmd_line, &cmd_info) == -1) )
return -1;

parse_cmd(cmd_line, &cmd_info);



if (!strcmp(cmd_info.arg[0], "exit"))
exit(0);

pid_t pid = exec_simple(&cmd_info);

waitpid(pid, NULL, 0);
}

return 0;
}

谢谢。

最佳答案

问题出在 cmd_info->arg 上,它被声明为 char **arg 并且您永远不会为它分配内存。

因此,当您尝试访问它以保存像这样的参数时 cmd_info->arg[iarg++] = args[i],您正在取消引用未初始化的指针,从而导致段错误。

一种解决方案是更改 Command_Info 结构以声明 arg,如下所示:

char *arg[MAX_ARG_LENGTH];

关于c - 帮助简单的 linux shell 实现,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/2647663/

25 4 0
Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
广告合作:1813099741@qq.com 6ren.com