linux下自行实现的简单shell程序

学过exec系列函数后,我尝试自行实现一个shell程序,
先上代码

#include<iostream>
#include<string>
#include<cstring>
#include<cstdio>
#include<stdlib.h>
#include<sys/wait.h>
#include<sys/types.h>
#include<unistd.h>

#define Num 32;
using namespace std;
int main()
{
	char buff[1024]={0};
	for(;;){
	string tips = " [XXX@host_local YYY]# ";
	cout << tips;
	fgets(buff,sizeof(buff)-1,stdin);
	buff[strlen(buff)-1] = 0;
	char *argv[Num];
	argv[0] = strtok(buff," ");
	int i=0;
	while(argv[i]!=NULL){
		i++;
		argv[i] = strtok(buff," ");
	}
	pid_t id=0;
	if(id==0){
		cout << " child is running ..." << endl;
		execv(argv[0],argv);
		exit(123);
		}
	else{
		int status=0;
		waitpid(id,&status,0);
		cout << " code erro:" << WEXETSTATUS(status)<< endl;
	}
	}
	return 0;
}

大致思路:
要想写出一个和系统类似的shell,我们需要:

  1. 写入命令行
  2. 解析命令行
  3. 建立子进程
  4. 替换子进程
  5. 父进程等待子进程退出

写入命令行
首先我们需要写一个格式如操作系统内核的shell , [XXX@host_local YYY]# ,来提示我们接下来要输出命令,打印出来,下来就是要写入操作了,那么这个操作是由用户自行写入,也就是要从键盘上写入,我们使用了函数fgets(),这时候注意,用户在键盘输入是,最后是以回车提交,而如果fgets()会把回车一并读取上来,所以我们手动把buff数组的最后一个元素设置为0才行。
解析命令行
要解析我们刚刚写入的命令,就要用到strtok函数,以空格为分隔符将刚刚写入的buff数组解析到新数组argv[ ]中,循环写入,需要注意的是,strtok函数会把分割前的字符串破坏掉,即每次分割后,原来的字符串就会少掉一部分,完整性会被破坏。
建立子进程
这个程序的主要目的,就是创建一个子进程,让这个子进程替换成我们写入的命令行,也是体现整个代码核心思想的代码段,用到了execv()函数,此时传入的第一个参数,就是刚刚收到命令行解析的argv[ ]数组的首元素,第二个参数就是argv这个数组。

父进程等待子进程退出
最后父进程等待子进程退出,

发布了34 篇原创文章 · 获赞 4 · 访问量 1741

猜你喜欢

转载自blog.csdn.net/qq_41181857/article/details/104783047