vfork导致父进程环境变量被修改

2019-10-24  本文已影响0人  xiabodan

vfork版本

#include <stdio.h>
#include <stdlib.h>
#include <assert.h>
#include <sys/types.h>
#include <unistd.h>

static int childProcess(void *arg) {
    char* env = getenv("MY_ENV");
    printf("childProcess %d env:%s\n", getpid(), env);
    setenv("MY_ENV", "helloword", 1); 
    exit(0);
}
int main(void) {

    volatile pid_t resultPid = vfork();
    if (resultPid == 0) {
        childProcess(NULL);
    }   
    volatile pid_t resultPid1 = vfork();
    if (resultPid1 == 0) {
        childProcess(NULL);
    }   
    char* env = getenv("MY_ENV");
    printf("main process %d env:%s\n", getpid(), env);
    assert(resultPid != 0); /* childProcess never returns */
    assert(resultPid1 != 0); /* childProcess never returns */
    return 0;
}

运行结果

childProcess 12451 env:(null)
childProcess 12452 env:helloword
main process 12450 env:helloword

可以看出,父进程没有设置环境变量MY_ENV,但是由于子进程12451 设置了环境变量,导致主进程12450 也被设置了。

fork版本

// vfork.c
static int childProcess(void *arg) {
    char* env = getenv("MY_ENV");
    printf("childProcess %d env:%s\n", getpid(), env);
    setenv("MY_ENV", "helloword", 1);
    exit(0);
}
int main(void) {
    // volatile pid_t resultPid = vfork();
    volatile pid_t resultPid = fork();
    if (resultPid == 0) {
        childProcess(NULL);
    }
    // volatile pid_t resultPid1 = vfork();
    volatile pid_t resultPid1 = fork();
    if (resultPid1 == 0) {
        childProcess(NULL);
    }
    char* env = getenv("MY_ENV");
    printf("main process %d env:%s\n", getpid(), env);
    assert(resultPid != 0); /* childProcess never returns */
    assert(resultPid1 != 0); /* childProcess never returns */
    return 0;
}

运行结果

main process 14304 env:(null)
childProcess 14305 env:(null)
childProcess 14306 env:(null)

可以看出,即使子进程设置了环境变量,但是并没有影响其他子进程。

vfork + execve版本

#include <stdio.h>
#include <stdlib.h>
#include <assert.h>
#include <sys/types.h>
#include <unistd.h>

static int childProcess(void *arg) {
    char *argVec[10]; //参数数组
    char *envVec[] = {"环境参数1","环境参数2",NULL}; //环境变量数组
    printf("childProcess %d exec\n", getpid());
    execve("./exec", argVec,envVec);
}
static int childProcess1(void *arg) {
    char* env = getenv("MY_ENV");
    printf("childProcess %d env:%s\n", getpid(), env);
    // setenv("MY_ENV", "helloword", 1);
    exit(0);
}
int main(void) {
    volatile pid_t resultPid = vfork();
    // volatile pid_t resultPid = fork();
    if (resultPid == 0) {
        childProcess(NULL);
    }   
    sleep(1);
    volatile pid_t resultPid1 = vfork();
    // volatile pid_t resultPid1 = fork();
    if (resultPid1 == 0) {
        childProcess1(NULL);
    }   
    char* env = getenv("MY_ENV");
    printf("main process %d env:%s\n", getpid(), env);
    assert(resultPid != 0); /* childProcess never returns */
    assert(resultPid1 != 0); /* childProcess never returns */
    return 0;
}
// exec.c
#include <stdio.h>
#include <stdlib.h>
#include <assert.h>

#include <sys/types.h>
#include <unistd.h>

int main() {
    char* env = getenv("MY_ENV");
    printf("childProcess %d env :%s\n", getpid(), env);
    setenv("MY_ENV", "helloword", 1); 
    // char* env1 = getenv("MY_ENV");
    // printf("childProcess %d env1:%s\n", getpid(), env1);
    return 0;
}

运行结果

childProcess 16605 exec
childProcess 16605 env :(null)
childProcess 16606 env:(null)
main process 16604 env:(null)

子进程在执行完execve后,修改环境变量对主进程已经没有影响。

结论:

上一篇 下一篇

猜你喜欢

热点阅读