6.s081 lab1--util笔记

这篇博客详细介绍了命令行参数如何从shell传递到目标程序,涉及fork、execve、加载器和_start函数。讨论了sleep、pingpong(管道通信)、寻找素数的算法、find命令的实现细节,以及xargs如何处理标准输入作为参数。同时,提到了文件系统中的inode、dirent和stat结构体的作用。
摘要由CSDN通过智能技术生成

lab1—util

在开始之前有必要先了解一下当我们在命令行中输入的参数如何被传递给程序的。为此我参考了csapp的内容。

当你在命令行中输入了一行命令字符串然后按下enter键后,shell程序首先解析你输入的一行命令字符串,解析程序将你输入的那行字符串存储在一个字符数组argv中,argv数组如下图所示。数组的每一个元素都是你的输入的一部分。然后shell程序根据argv[0]判断这个命令是否是shell内置命令,如果是shell内置命令那么直接执行shell内置的指令,如果不是shell内置命令那么shell程序调用fork()创建一个子进程,然后在这个子进程中调用execve()函数,例如:execve(argv[0], argv, environ),environ类似于argv,如下图所示它里面存储的是环境变量字符串数组。execve函数加载并执行可执行文件argv[0],下面简单说一下加载的过程。

在这里插入图片描述

这个加载的过程是通过操作系统中称为加载器的程序来完成的,加载器删除子进程现有的虚拟内存段,并创建一组新的代码、数据、堆和栈段。新的栈和堆段被初始化为零。通过将虚拟地址空间中的页映射(注意,不是直接复制)到可执行文件的页大小的片,新的代码和数据段被初始化为可执行文件的内容。最后,加载器跳转到_start函数的地址,这个函数是在系统目标文件ctrl.o中定义的。_start函数调用函数__libc_start_main,这个函数定义在libc.so中,它初始化执行环境(设置栈,也就是main的参数,将栈设置成如下图所示),调用用户层的main函数,处理main函数的返回值,并在需要的时候把控制返回给内核。

在这里插入图片描述

也就是说,我们在命令行中传递的参数依次传递给了shell,shell的命令解析器,execv函数,加载器,_start函数,libc_start_main函数,最后传递给了我们要执行的命令的main函数。

sleep

#include "kernel/types.h"
#include "kernel/stat.h"
#include "user/user.h"

int main(int argc, char *argv[])
{
   
        int i;
        const char *str = "sleep: usage: sleep [integer]\n";
        if (argc != 2){
   
                write(1, str, strlen(str));
                exit(0);
        }
        i = atoi(argv[1]);
        sleep(i);
        exit(0);
        return 0;
}

从命令行中传递给argv的时间参数是个字符串,根据提示调用atoi函数即可转换为整型。然后调用sleep函数即可。

pingpong

#include "kernel/types.h"
#include "kernel/stat.h"
#include "user/user.h"

int main(int argc, char *argv[])
{
   
        int pfd[2];
        int cfd[2];
        int pid;
        char buff[1];
        if (argc != 1){
   
                fprintf(2, "pingpong: usage: pingpong\n", 26);
                exit(1);
        }
        pipe(pfd); 
        pipe(cfd); 
        if ((pid = fork()) == 0){
   
                close(pfd[1]);
                close(cfd[0]);
                if (read(pfd[0], buff, 1) == 1){
   
                        printf("%d: received ping\n", getpid());
                        write<
  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值