操作系统与系统编程(四)系统调用常用方法

系统调用的常用方法:

一.系统调用方法用来运行不同的程序,格式为:

int execve(const char* filename, char* const argv[], char* const envp[]);

​ 该方法以argv为参运行filename指向的可执行程序,并将envp存储的“变量=数值”对作为环境变量代入这个程序。argv的第一个参数必须与filename一致,真正的参数从第二个开始。

注意!!

​ 该方法会让filename的程序覆盖进程中正在运行的程序,因此该方法后的代码无法被执行(除非该方法运行失败)

二.在 Linux 系统中,比起系统调用更常使用以exec开头的六个函数:

int execl(const char* path, const char* arg, ...);
int execlp(const char* file, const char* arg, ...);
int execle(const char* path, const char* arg,
           ..., char* const envp[]);
int execv(const char* path, char* const argv[]);
int execvp(const char* file, char* const argv[]);
int execvpe(const char* file, char* const argv[],
            char* const envp[]);

​ 它们都具有系统调用功能,可将这些函数表示为:“exec + l/v + p/e/pe”,这六个函数主要有两处不同:

​ 第一处不同(l/v)——“l”类函数将所有参数作为一整个字符串代入,而“v”类函数将参数分别放入一个字符串数组中,将数组作参代入函数运行

​ 第二处不同(p/e/pe)——包含 p的函数可以模仿计算机中壳功能,在“file”中不含“/”时使用环境变量 PATH 中的目录来寻找可执行文件,包含 e的函数可以像execve一样将“变量=数值”对作为环境变量代入程序

三.用法

​ 使用系统调用函数一般先调用fork()产生新进程,然后再新进程中用exec()类函数运行新程序。

​ 可能大家有疑问,调用fork()会复制了全部父进程地址空间又弃置,会造成浪费。

​ 其实, Linux 系统采用了 copy_on_write 技术,只有在某一数据被修改时那个数据才会被实际复制到子进程的地址空间。所以在fork()之后直接运行exec()时,父进程的地址空间不会被复制过来。

举个栗子:

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

int count = 0;

int main(){

    int pid = fork();
    if (pid==0){
        count++;
        int pid2 = fork();
        if (pid2 == 0){
            char** argv = (char**) malloc(3*sizeof(char*));
            argv[0] = "echo";
            argv[1] = "Hello!";
            argv[2] = NULL;
            int pid3 = fork();
            count++;
            if (pid3 == 0){
                count++;
                execvp("echo", argv);
                printf("Count %d,",count);
                exit(0);
            } else {
                free(argv);
                wait(NULL);
                printf("%d,",count);
                exit(0);
            }
        } else {
            wait(NULL);
            printf("%d,",count);
            exit(0);
        }
    } else {
        wait(NULL);
        printf("%d.",count);
        return 0;
    }    
}

​ 最后输出为:hello!

​ 2,1,0.

转载请注明出处!!!

如果有写的不对或者不全面的地方 可通过主页的联系方式进行指正,谢谢

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值