2015-11-19 42 views
1

到目前为止,我的代码在用户输入时处理ls命令。我希望能够处理像ls -l /tmp这样的命令。 我的代码到目前为止。处理命令,如ls -l/somedir

#include <stdio.h> 
#include <string.h> 
#include <unistd.h> 
#include <stdlib.h> 
#include <sys/wait.h> 
#include <stdarg.h> 
#include <sys/types.h> 


int main(void) 
{ 
for(;;){ 
char str[500]; 
printf("Type a command : \n"); 
scanf("%s",str); 
char *path; 
    path = getenv("PATH"); 
    char *argv[] = { path ,NULL}; 

    int status; 
    int pid = fork(); 

     if (pid == 0) { 
printf("executing==============> %s \n",str); 
      execvp(str,argv); 
} 
wait(&status); 
} 
} 

任何想法?我必须这样做,没有system()

+1

首先,你应该使用'scanf函数( “%s” 时,STR);'代替。你的代码工作,因为在这种情况下,'str'和'&str'具有相同的地址。 当你调用'execvp'时,你需要传递你想运行的命令和一个字符串数组作为参数,每个字符串都是该命令的一个参数。 P.S .:通常用所需的命令启动阵列。例如'char * argv [] = {str,“-l”,“/ tmp”,NULL};' – ddz

+0

'char * argv [] = {str,“-l”,“/ tmp”,NULL}; '当我输入'ls'时,它直接执行'ls -l/tmp'。我想要的是能够像'ls','pwd' **和'ls -l/somedir' @LuizEduardoF这样的命令来处理命令。 –

+0

请参阅下面的答案。 – ddz

回答

0

这为我工作:

所有的
#include <stdio.h> 
#include <string.h> 
#include <unistd.h> 
#include <stdlib.h> 
#include <sys/wait.h> 
#include <stdarg.h> 
#include <sys/types.h> 
#define MAX_NAME_SZ 256 

int main(void) 
{ 
char *str,*ret, *pa1, *pa2, *dtm ,*pa3; 
str=(char *)malloc(50*sizeof(char)); 
ret=(char *)malloc(50*sizeof(char)); 
pa1=(char *)malloc(50*sizeof(char)); 
pa2=(char *)malloc(50*sizeof(char)); 
dtm=(char *)malloc(50*sizeof(char)); 
pa3=(char *)malloc(50*sizeof(char)); 
char ch =' ' ; 
printf("Type a command : \n"); 

    fgets (str, MAX_NAME_SZ, stdin); 

    if ((strlen(str)>0) && (str[strlen (str) - 1] == '\n')) 
     str[strlen (str) - 1] = '\0'; 
    ret = strchr(str, ch); 

    if (ret !=NULL) 
    { 
     strcpy(dtm, str); 
     sscanf(dtm, "%s %s %s ", pa1, pa2,pa3 ); 
     } 

    char *path; 
    path = getenv("PATH"); 

    int status=2; 
    int pid = fork(); 

    if (pid == 0) { 
     if (ret !=NULL){ 
      char *argv[] = { path ,pa2, pa3 ,NULL}; 
       execvp(pa1,argv); 

       } 
     else { 
      char *argv[] = { path ,NULL}; 
      execvp(str,argv); 

     } 
    } 
    wait(&status); 

    } 
2

execvp系统调用期望作为其参数的一个字符串,该命令包含一个字符串数组,该数组字符串以该命令开头,后面跟着参数,一个接一个,以NULL字符串结尾。

在你的情况,这将是:

char *argv[] = {"ls", "-l", "/tmp", NULL}; 

请记住,这段代码只是什么是幕后的说明。您需要根据用户的输入构建argv[]

您可以合并strchr()以标记输入(查找空格),然后使用sscanf来读取字符串的一部分。然后,您必须将输入指针更新为由strchr() + 1返回的值,并使用sscanf()来读取命令的下一部分。

1

您可以轻松地使用system(str)来做到这一点。

它叉,呼叫execl("/bin/sh", "sh". "-c", command, (char *) 0);并在命令完成后返回。

当它调用shell时,它也支持shell内置函数。

+0

我必须在没有'system()'的情况下执行它。 –

+0

使用'system(command)'使你的程序在那一刻停下来,等待'command'执行。使用fork()来执行它可以让你的进程创建一个子进程,并使用子进程PID为你运行另一个程序,因此如果主进程想要做别的事情,主进程不必等待子进程退出。另外,你应该考虑'execvp()'系统调用的影响。 – ddz

0

使用相同的“系统”功能。系统(str)应该可能工作。 该函数创建一个单独的线程,执行提供给它的命令。 有关详细信息,请参阅“man system”。

+0

我必须在没有'system()'的情况下执行它。 –