shell的簡單實現

來源:互聯網
上載者:User

標籤:style   blog   color   io   使用   ar   strong   for   檔案   

shell是Unix/Linux中的重要工具,用來解析使用者輸入的命令。下面我們來實現一個簡單的shell程式,來練習fork/exec/wait/exit的使用,順便推薦一本書籍《Understanding Unix/Linux Programming - A Guide to Theory and Practice》,這本書寫的非常好,適合Unix/Linux系統編程初學者使用。

下面是我們shell的主程式:

 1 int main(void) 2 { 3     char *cmdline; 4     char *prompt; 5     char **arglist; 6     int result; 7  8     prompt = PROMPT; 9     signal(SIGINT, SIG_IGN);10     signal(SIGQUIT,SIG_IGN);11 12     while ((cmdline = next_cmd(prompt, stdin)) != NULL) {13         if ((arglist = split_line(cmdline)) != NULL) {14             result = execute(arglist);15             freelist(arglist);16         }17         free(cmdline);18     }19 20     return 0;21 }

其中,next_cmd()函數的主要功能是從輸入資料流中讀入下一個命令,碰到檔案結束符返回NULL。下面是該函數的代碼:

 1 char *next_cmd(char *prompt, FILE *file) 2 { 3     char *cmdline; 4     int  length = 0; 5     int  c; 6     int  location = 0; 7  8     printf("%s", prompt); 9 10     while ((c = getc(file)) != ‘\n‘) {11         if (location + 1 >= length) {12             cmdline = (char *)malloc(BUFSIZ);13             length = BUFSIZ;14         } 15         else if (location >= BUFSIZ) {16             cmdline = realloc(cmdline, length + BUFSIZ);17             length += BUFSIZ;18         }19         cmdline[location++] = c;20     }21     cmdline[location] = ‘\0‘;22 23     return cmdline;24 }

split_line()函數的主要功能是將輸入的一行字串拆解成字串數組,該字串數組以NULL結束。下面是該函數的代碼:

 1 char **split_line(char *cmd) 2 { 3     char **arglist; 4     int  row = 0; 5     int  len = 0; 6     char *cp = cmd; 7     char *start = cmd; 8     arglist = malloc(BUFSIZ); 9 10     while (*cp != ‘\0‘) {11         while (*cp != ‘ ‘ && *cp != ‘\t‘) {12             ++cp;13             ++len;14         }15         arglist[row] = malloc(len + 1);16         strncpy(arglist[row], start, len);17         ++row;18         len = 0;19         while (*cp == ‘ ‘ || *cp == ‘\t‘) {20             ++cp;21         }22         start = cp;23     }24     arglist[row] = NULL;25 26     return arglist;27 }

execute()函數的主要功能是使用fork, execvp和wait函數來運行一個命令,並返回命令的結束狀態。下面該函數的代碼:

 1 int execute(char **argv)  2 { 3     pid_t pid; 4     int child_info = -1; 5  6     if ((pid = fork()) == -1) { 7         perror("fork error"); 8     } 9 10     if (pid == 0) {11         signal(SIGINT, SIG_DFL);12         signal(SIGQUIT, SIG_DFL);13         execvp(argv[0], argv);14         perror("exec error");15         exit(1);16     }else {17         if (wait(&child_info) == -1) {18             perror("wait error");19         }20     }21 22     return child_info;23 }

freelist()函數是釋放上面分配的字串數組的空間。下面是該函數的代碼:

 1 void freelist(char **list)  2 { 3     char **cp = list; 4     while (*cp) { 5         free(*cp); 6         ++cp; 7     } 8  9     free(list);10 }

由於個人水平有限,歡迎討論,非喜勿噴,thank you!!

shell的簡單實現

相關文章

聯繫我們

該頁面正文內容均來源於網絡整理,並不代表阿里雲官方的觀點,該頁面所提到的產品和服務也與阿里云無關,如果該頁面內容對您造成了困擾,歡迎寫郵件給我們,收到郵件我們將在5個工作日內處理。

如果您發現本社區中有涉嫌抄襲的內容,歡迎發送郵件至: info-contact@alibabacloud.com 進行舉報並提供相關證據,工作人員會在 5 個工作天內聯絡您,一經查實,本站將立刻刪除涉嫌侵權內容。

A Free Trial That Lets You Build Big!

Start building with 50+ products and up to 12 months usage for Elastic Compute Service

  • Sales Support

    1 on 1 presale consultation

  • After-Sales Support

    24/7 Technical Support 6 Free Tickets per Quarter Faster Response

  • Alibaba Cloud offers highly flexible support services tailored to meet your exact needs.