要模拟实现shell,我们首先要搞清楚它是怎么工作的,在Linux操作系统下:
首先,shell先读入命令,然后创建子进程,让子进程完成读入的命令,这就需要用到进程替换,让子进程执行另一段程序;而父进程负责等待子进程的结束,子进程结束后,就可以读取新的命令了。
下面就是具体的实现:
#include <stdio.h> #include <assert.h> #include <unistd.h> #include <sys/wait.h> #include <stdlib.h> #include <string.h> char* argv[8];//定义命令行参数列表 int argc = 0; //定义命令行参数个数 void do_phrase(char buf[]) { assert(buf); //将buf数组中的内容加到命令行参数列表中 int i = 0; int status = 0; for(argc = i = 0; i < 8; ++i) { if(buf[i] != ' ' && status == 0) { argv[i] = &buf[i]; argc++; status = 1; } else if(buf[i] == ' ') { status = 0; buf[i] = 0; //每个字符串的结束 } } argv[argc] = NULL; } void do_execute() { //先创建一个进程 int pid = fork(); switch(pid) { case -1: perror("fork"); break; case 0: //在子进程中进行程序替换,执行另一串命令 execvp(argv[0], argv); //未进行程序替换成功,走到这一步 perror("execvp"); exit(EXIT_FAILURE); break; default: //在父进程中等待子进程执行结束 { int st = 0; int ret = wait(&st); while(ret != pid); break; } } } int main() { char buf[1024] = {}; while(1) { printf("myshell>"); scanf("%[^\n]%*c", buf); //获取字符 do_phrase(buf); //解析字符 do_execute(); //程序替换 } return 0; }