Linux:进程(二)
创始人
2024-04-12 04:21:39
0

文章目录

  • 前言
  • 一、环境变量
    • 1.概念
    • 2.常见环境变量
    • 3.一个疑问
    • 4.通过系统调用获取或设置环境变量
  • 二、地址空间
    • 1.引入
    • 2.分页&进程地址空间
      • 1.页表
      • 2.写时拷贝
    • 3.为什么要有地址空间
  • 总结


前言

  今天我们继续学习进程相关知识。


一、环境变量

1.概念

  1. 环境变量(environment variables)一般是指在操作系统中用来指定操作系统运行环境的一些参数
  2. 如:我们在编写C/C++代码的时候,在链接的时候,从来不知道我们的所链接的动态静态库在哪里,但是照样可以链接成功,生成可执行程序,原因就是有相关环境变量帮助编译器进行查找
  3. 环境变量通常具有某些特殊用途,还有在系统当中通常具有全局特性

2.常见环境变量

PATH : 指定命令的搜索路径
HOME : 指定用户的主工作目录(即用户登陆到Linux系统中时,默认的目录)
SHELL : 当前Shell,它的值通常是/bin/bash。

3.一个疑问

为什么有些指令可以直接执行,不需要带路径,而我们的二进制程序需要带路径才能执行?

  1. 执行程序前,系统会在特定路径下查找对应程序
  2. 而PATH的作用是辅助系统进程指令查找,PATH变量储存的就是可能存在指令或者程序的路径

也就是说,如果我们把自己程序所在路径加入环境变量PATH当中,就可以直接执行。
测试:

[wkj@VM-4-13-centos ~]$ export PATH=$PATH:/home/wkj/lesson8
[wkj@VM-4-13-centos lesson8]$ ll
total 36
-rw-rw-r-- 1 wkj wkj   77 Nov  7 18:22 makefile
-rwxrwxr-x 1 wkj wkj 8464 Nov 12 21:23 myproc
-rw-rw-r-- 1 wkj wkj  169 Nov 12 21:23 myproc.c
-rwxrwxr-x 1 wkj wkj 9616 Nov 12 19:44 mytest
-rw-rw-r-- 1 wkj wkj  243 Nov 12 19:43 mytest.c
[wkj@VM-4-13-centos lesson8]$ myproc
hello world,20905 
hello world,20905 
hello world,20905 

注意看,添加以后不需要./即可直接执行。
添加方法只在当前有用,退出登陆后不会保存,因此大家可以添加以下玩一玩,不用担心污染环境变量库。

4.通过系统调用获取或设置环境变量

#include 
#include 
int main()
{printf("%s\n", getenv("PATH"));return 0;
}

常用getenv和putenv函数来访问特定的环境变量。

tips:环境变量通常具有全局属性,可以被子进程继承下去

二、地址空间

我们经常在各个论坛看到类似以下的图片。
在这里插入图片描述

1.引入

#include 
#include 
#include 
int g_val = 0;
int main()
{pid_t id = fork();if(id < 0){perror("fork");return 0;
}
else if(id == 0){ //childprintf("child[%d]: %d : %p\n", getpid(), g_val, &g_val);
}else{ //parentprintf("parent[%d]: %d : %p\n", getpid(), g_val, &g_val);
}sleep(1);return 0;
}

与环境相关,我们观察现象即可
parent[2995]: 0 : 0x80497d8
child[2996]: 0 : 0x80497d8

我们发现,输出出来的变量值和地址是一模一样的,很好理解呀,因为子进程按照父进程为模版,父子并没有对变量进行任何修改。可是将代码稍加改动:

#include 
#include 
#include 
int g_val = 0;
int main()
{pid_t id = fork();if(id < 0){perror("fork");return 0;
}
else if(id == 0){ //child,子进程肯定先跑完,也就是子进程先修改,完成之后,父进程再读取g_val=100;printf("child[%d]: %d : %p\n", getpid(), g_val, &g_val);
}else{ //parentsleep(3);printf("parent[%d]: %d : %p\n", getpid(), g_val, &g_val);
}sleep(1);return 0;
}

与环境相关,我们观察现象即可
child[3046]: 100 : 0x80497e8
parent[3045]: 0 : 0x80497e8

怎么回事呢?地址一样,变量内容不一样,我接受不了哇!

我们可以得出以下结论:

  1. 变量内容不一样,所以父子进程输出的变量绝对不是同一个变量地址值是一样的,说明,该地址绝对不是物理地址。
  2. 在Linux地址下,这种地址叫做 虚拟地址。
  3. 我们在用C/C++语言所看到的地址,全部都是虚拟地址!物理地址,用户一概看不到,由OS统一管理。
  4. OS必须负责将 虚拟地址 转化成 物理地址 。

2.分页&进程地址空间

1.页表

页表就是一个用于将虚拟地址转换为物理地址的工具。在 riscv32 中,如果 satp 的第 31 位为 1 ,则表示启用页表机制。在访问虚拟内存时(开启页表时只允许访问虚拟内存),内存管理单元 MMU(Memory Management Unit) 会用过页表将虚拟地址转换为物理地址,再进行访问。

在这里插入图片描述

2.写时拷贝

一个变量为什么可以标识不同的值?

父子进程各自在物理内存中,都有属于自己的变量空间,只不过在用户层用同一个变量(虚拟地址)来标识了。

3.为什么要有地址空间

  1. 凡是非法的访问或者映射,OS都可以设备到,并终止这个进程。
  2. 因为有地址空间、页表,在物理内存中,可以堆未来的数据进行任意位置的加载。
  3. 物理内存理论上可以进行任意位置加载,那么他很可能是乱序的。页表将虚拟地址和物理地址进行映射,内存分布可以有序化。

总结

以上就是今天要讲的内容啦。
在这里插入图片描述

相关内容

热门资讯

和解方案遭拒:多位作家再次起诉... 此次起诉作家的部分作品。 据《出版人周刊》报道,近期六位作家分别针对Anthropic、OpenAI...
欧林生物(688319)披露涉... 截至2025年12月30日收盘,欧林生物(688319)报收于25.32元,较前一交易日下跌0.74...
高新发展:华惠嘉悦汇广场合同纠... 观点网讯:12月30日,成都高新发展股份有限公司(高新发展)发布公告,披露其全资子公司成都倍特建筑安...
我国首例AI幻觉引发的侵权纠纷... 12月29日晚,杭州互联网法院公开了一起关于AI幻觉的网络侵权纠纷案的审判情况。 2025年6月,...
原创 滨... 鲁网12月30日讯12月29日,滨州市召开高质量完成“十四五”规划主题系列新闻发布会第五场——“平安...
制度供给,邮轮经济有了“上海模... 图为吴淞口国际邮轮港,今年前三季度,靠泊邮轮177艘次,占全国市场六成。/采访对象提供 邮轮经济产业...
西藏深耕新时代“枫桥经验” 多... 中新网拉萨12月30日电 (贡嘎来松)30日,西藏自治区司法厅召开西藏自治区调解工作基本情况新闻发布...
浦东建设(600284)披露修... 截至2025年12月30日收盘,浦东建设(600284)报收于8.55元,较前一交易日上涨1.06%...
中钢国际(000928)发布现... 截至2025年12月30日收盘,中钢国际(000928)报收于6.56元,较前一交易日下跌1.5%,...