使用進程創建,進程等待和程序替換函數能實現一個低配版的shell
1 #include<stdio.h>
2 #include<stdlib.h>
3 #include<string.h>
4 #include<unistd.h>
5 #include<sys/wait.h>
6 //intput 表示待切分命令
7 //output 表示切分結果(字符串數組)
8 //返回值表示output中包含了幾個有效元素
9 int Split(char intput[],char* output[])
10 {
11 char* p=strtok(intput," ");
12 int i=0;
13 while(p!=NULL)
14 {
15 output[i]=p;
16 ++i;
17 p=strtok(NULL," ");
18 }
19 output[i]=NULL;//這個操作很容易被忘記
20 return i;
21 }
22
23 void CreateProcess(char* argv[],int n)
24 {
25 (void) n;
26 //1.創建子進程
27 pid_t ret=fork();
28 //2.父進程進行進程等待,子進程進行程序替換
29 if(ret>0)
30 {
31 //father
32 //暫時先這麼寫,正常的話一個shell
33 //是應該知道子進程的退出碼
34 wait(NULL);
35 }
36 else if(ret==0)
37 {
38 //child
39 ret=execvp(argv[0],argv);
40 //if條件可以省略,如果exec成功了
41 //是肯定不會執行到這個代碼的
42 perror("exec");
43 exit(0);
44 }
45 else{
46 perror("fork()");
47 }
48 }
49
50
51 int main()
52 {
53 while(1)
54 {//1.打印提示符
55 printf("[---@localhost]$ ");
56 fflush(stdout);
57 //2.用戶輸入一個指令
58 char command[1024]={0};
W> 59 gets(command);//一次讀一行數據
60 //3.解析指令,把要執行那個程序識別出來
61 //那些是命令行參數識別出來 (字符串切分)
62 //切分結果應該是一個字符串數組
63 char* argv[1024];
64 int n=Split(command,argv);
65 CreateProcess(argv,n);
66 }
67 return 0;
68 }
myshell的改進點:
1.自動獲取用戶名,主機名,當前路徑
2.需要支持cd命令 cd該的子進程的當前路徑,子進程修改不會影響到父進程
需要讓父進程直接支持cd(而不是創建子進程/程序替換)
內建命令
3. 支持定義別名ll其實是ls -l (需要在程序中維護一個鍵值對數據結構)
std::map
4.支持管道
5.支持重定向