【Linux】--- 制作一个简易的shell
制作一个简易的shell
- 一、设置命令行
- 二、获取输入的命令
- 第一步和第二步代码细节剖析
- 三、命令行字符串分割
- 第三步细节剖析
- 四、执行命令
- 五、代码汇总及演示
想要制作一个简易的shell,过程分为四步
一、设置命令行
#include<stdio.h>
#include<stdlib.h>
#include<string.h>
#include<sys/types.h>
#include<unistd.h>
#include<sys/wait.h>
#include<errno.h>
#define SIZE 512
#define SEP " "
#define ZERO '\0'
#define NUM 32
const char *get_username()
{
const char *name=getenv("USER");
if(name==NULL) return "None";
return name;
}
const char *get_hostname()
{
const char *hostname=getenv("HOSTNAME");
if(hostname==NULL) return "None";
return hostname;
}
const char *get_cwd()
{
const char* cwd=getenv("PWD");
if(cwd==NULL) return "None";
return cwd;
}
void make_commandline_and_print()
{
char line[SIZE];
const char *username=get_username();
const char *hostname=get_hostname();
const char *cwd=get_cwd();
snprintf(line,sizeof(line),"[%s@%s %s]> ",username,hostname,cwd);
printf("%s",line);
fflush(stdout);
}
int main()
{
// 设置命令行
make_commandline_and_print();
return 0;
}
二、获取输入的命令
int get_user_command(char command[],size_t n)
{
char *s=fgets(command,n,stdin);
if(s==NULL) return -1;
command[strlen(command)-1]=ZERO;
return strlen(command);
}
int main()
{
char usercommand[SIZE];
int n=get_user_command(usercommand,sizeof(usercommand));
return 0;
}
第一步和第二步代码细节剖析
三、命令行字符串分割
void split_command(char command[],size_t n)
{
// 先处理第一个
Argv[0]=strtok(command,SEP);
int index=1;
while((Argv[index++]=strtok(NULL,SEP)));
// 特意设置=,先赋值,再判断,分割之后strtok会返回NULL,
// 刚好Argv的最后一个元素是NULL,判断结束
}
int main()
{
split_command(usercommand,sizeof(usercommand));
return 0;
}
第三步细节剖析
四、执行命令
void Die()
{
exit(1);
}
void executecommand()
{
pid_t id=fork();
if(id<0) Die();
else if(id==0)
{
// child
execvp(Argv[0],Argv);
exit(errno);
}
else{
// father
int status=0;
pid_t rid=waitpid(id,&status,0);
if(rid>0)
{
// TODO
}
}
}
int main()
{
executecommand();
return 0;
}
五、代码汇总及演示