现在的位置: 首页 > 综合 > 正文

c++调用shell 或者dos命令—使用system函数

2018年02月15日 ⁄ 综合 ⁄ 共 3725字 ⁄ 字号 评论关闭

c++调用shell 或者dos命令—使用system函数

 

转自:http://hi.baidu.com/jiangyangw3r/item/eedfba37b8dd6899b80c039e

相关函数<?XML:NAMESPACE PREFIX = O />

      fork,execve,waitpid,popen

表头文件

      #i nclude<stdlib.h>

定义函数

       int system(const char * string);

函数说明:

此函数用于调用c++调用shell 或者dos命令之用,system(char * )会调用fork()产生子进程,由子进程来调用/bin/sh-c string来执行参数string字符串所代表的命令,此命令执行完后随即返回原调用的进程。在调用system()期间SIGCHLD信号会被暂时搁置,SIGINT和SIGQUIT信号则会被忽略。

返回结果:system函数返回结果并非command命令的结果返回,而是返回shell的终止状态,而非执行命令字符串的终止状态, 根据具体情况,直接返回结果如下:

1,如果命令错误,如:system("tes -d ~/lib/atpkeylib.cpp");//这里tes命令根本不存在。

返回结果为:32512 。一个大于1的数。

2,如果命令正确,但是执行结果错误的话,如:system("test -d ~/lib/atpkeylib.cpp"); //路径下不存在atpkeylib.cpp文件,
返回结果为:256,高8位返回了,其实结果为256-255 =1 ;

3,如果命令正确,执行结果正确,如:system("test -d ~/home");

返回结果为:0;

4,如果system函数在调用fork函数时失败,则返回 -1;

注:‍system函数的返回值要分成两部分来说:

1,在程序中,用exit来设置进程的退出值时,虽然该函数的参数类型为int型,但再父进程中只能取到其值的低8位.所以用exit返回值时,高于255的值是没有意义的.

2,对于system函数,返回值是由两部分组成的,低8位值表示所执行的脚本在执行过程中所接收到的信号值,其余的位表示的脚本exit退出时所设置的值, 即脚本内exit退出是的值的低8位,在system返回值的低9-16位.

 

   system函数是由fork、execve和waitpid三个系统调用实现的。
      所以如果execve出错,则直接调用_exit(256),所以变量ret的值等于256
在system函数执行时,会启动一个子进程运行shell,然后通过将ls /tm作为参数传给shell,如果shell命令运行有错,就调用exit XXX作为system的返回值返回,而XXX是system函数的返回值,而不是shell运行ls /tm后的返回值。

 

 

经常性的,我们还是需要得到system函数执行字符串命令后的返回结果,那么请使用下面的几个宏:

WIFEXITED(status)如果子进程正常结束则为非0值。

WEXITSTATUS(status)取得子进程exit()返回的结束代码,一般会先用WIFEXITED 来判断是否正常结束才能使用此宏。

WIFSIGNALED(status)如果子进程是因为信号而结束则此宏值为真

WTERMSIG(status)取得子进程因信号而中止的信号代码,一般会先用WIFSIGNALED 来判断后才使用此宏。

WIFSTOPPED(status)如果子进程处于暂停执行情况则此宏值为真。一般只有使用WUNTRACED 时才会有此情况。

WSTOPSIG(status)取得引发子进程暂停的信号代码,一般会先用WIFSTOPPED 来判断后才使用此宏。

从上面的描述中我们可以看到,使用‍WIFEXITED(status) 来判断进程是否正常结束,之后使用‍WEXITSTATUS(status)来获得字符串命令返回的结果值,注意:‍若WIFEXITED返回0则用WEXITSTATUS来判断返回值没有意义。

--------------------------------------------------------------------------------------------------------------------------------------------------------------------------

我的例程1:

int main(){

‍int status = system("tes -d ~/lib/atpkeylib.cpp");
int status_01 =system("test -d ~/lib/atpkeylib.cpp");
int status_02 = system("test -d ~/avatar_server");
cout<<"wrong shell command:"<<endl;

       printf("%d\n", (status));
        printf("%d\n", WIFEXITED(status));
        printf("%d\n", WEXITSTATUS(status));
        printf("%d\n", WIFSIGNALED(status));
        printf("%d\n", WIFSTOPPED(status));
cout<<"wrong return data:"<<endl;
      printf("%d\n", (status_01));
        printf("%d\n", WIFEXITED(status_01));
        printf("%d\n", WEXITSTATUS(status_01));
        printf("%d\n", WIFSIGNALED(status_01));
        printf("%d\n", WIFSTOPPED(status_01));
cout<<"right return data:"<<endl;
       printf("%d\n", (status_02));
        printf("%d\n", WIFEXITED(status_02));
        printf("%d\n", WEXITSTATUS(status_02));
        printf("%d\n", WIFSIGNALED(status_02));
        printf("%d\n", WIFSTOPPED(status_02));

}

结果:

‍sh: tes: command not found
wrong shell command:
32512
1
127
0
0
wrong return data:
256
1
1
0
0
right return data:
0
1
0
0
0
--------------------------------------------------------------------------------------------------------------------------------------------------------------------------

我的例程2:

函数片段:

                       ‍check_auth = “test -d ~/home”;

    806             int status_01 = system(check_auth.c_str());
    807             if(WIFEXITED(status_01) == 0 ) //如果==0,为非正常退出
    808             {
    809                 set_error(ATPFS_USR_PWD_IS_WRONG); //抛出错误提示

‍                           return false;
    810             }
    811             if(WEXITSTATUS(status_01) == 1) //如果test命令执行结果为1,说明文件不存在啦。。。。。
    812             {
    813                 set_error(ATPFS_MOUNT_IS_NOT_EXIST);

                           return false;
    814             }
    815             if(WEXITSTATUS(status_01) == 0)   //如果test命令执行结果为0.,则说明文件存在
    816             {
                              return true;

                        }

注:如果想得到一个字符串命令的返回结果,可现在console下,执行该命令,之后使用echo $?来获得命令的执行结果。

抱歉!评论已关闭.