PHP实战

Linux system 函数

2016-11-26  本文已影响208人  小小小码农

最近工作中在Linux下,某些指定的程序需要调用指定的shell脚本完成指定工作,以前也曾经做过类似的功能,调用system函数执行指定的脚本,以前并不关心shell脚本是否执行成功了,现在的功能需要根据shell脚本执行成功与否,于是查询了下system函数的说明,有此文以做笔记之用。

system 函数说明

#include <stdlib.h>

int system(const char *command);

功能:调用/bin/sh -c 执行指定的脚本 command

常规使用方法:

int ret = system("./test.sh");

关于返回值:

如何判断脚本是否执行成功

答案是都错

system 返回值说明

man手册

The value returned is -1 on error (e.g. fork() failed), and the return status of the command otherwise. This latter return status is in the format specified in wait(2). Thus, the exit code of the command will be WEXITSTATUS(status). In case /bin/sh could not be executed, the exit status will be that of a command that does exit(127).If the value of command is NULL, system() returns non-zero if the shell is available, and zero if not.system() does not affect the wait status of any other children.

看着挺晕的,但是如果对于system的执行过程了解的话,就很容易理解了,函数执行分为以下几个阶段。
阶段1:创建子进程等准备工作。如果失败,返回-1
阶段2:调用/bin/sh拉起脚本,如果拉起失败或者shell未正常执行,原因值被写入ret中
阶段3:如果shell脚本执行成功,shell脚本的返回值写入ret中

从上面可知,不管shell脚本返回什么值,只要调用了/bin/sh,并且执行过程没有被信号中断,都算正常结束。因为脚本是在子进程中执行的,所以要想获取脚本是否执行成功的方法只能用系统提供的两个宏。

WIFEXITED用来判断阶段二的返回值
WEXITSTATUS用来判断阶段三的返回值

由于我们一般在shell中会通过返回值判断脚本是否执行成功,成功返回0,成功返回整数。所以判断一个脚本是否执行成功,应该满足三个条件:

注意:当shell脚本不存在时、没有执行条件等,前两个条件也会成立,此时WEXITSTATUS(ret)为127,所以shell脚本中不能将127作为返回值,shell脚本中的异常返回值最好从1开始递增,成功返回0。

实例代码

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


int main(int argc, char *argv[])
{

    pid_t status;


    status = system("./test.sh");

    if (-1 == status)
    {
        printf("system error!");
    }
    else
    {
        printf("exit status value = [0x%x]\n", status);

        if (WIFEXITED(status))
        {
            if (0 == WEXITSTATUS(status))
            {
                printf("run shell script successfully.\n");
            }
            else
            {
                printf("run shell script fail, script exit code: %d\n", WEXITSTATUS(status));
            }
        }
        else
        {
            printf("exit status = [%d]\n", WEXITSTATUS(status));
        }
     }
     return 0;
}

总结

system用起来,看则简单,实则不那么简单,有很多隐藏的坑,需要自己深入理解原理,才能更好地使用,也可以用其他实现方式完成相同的功能。
最后对自己说,多写,多思,多总结

上一篇 下一篇

猜你喜欢

热点阅读