使用 Shell 脚本实现一个简单 Docker
《使用 Shell 脚本实现 Docker》旨在通过一系列的实验使用户对docker的底层技术,如Namespace、CGroups、rootfs、联合加载等有一个感性的认识。在此过程中,我们还将通过Shell脚本一步一步地实现一个简易的docker,以期使读者在使用docker的过程中知其然知其所以然。
我们的实验环境为Ubuntu 18.04 64bit,简易docker工程的名字为 docker.sh,该工程仓库地址如下:
https://github.com/pandengyang/docker.sh.git
https://github.com/appotry/docker.sh《使用 Shell 脚本实现 Docker》目录如下:
1. Namespace
1.1. Namespace简介
1.2. uts namespace
1.2.1. uts namespace简介
1.2.2. docker.sh
1.3. mount namespace
1.3.1. /etc/mtab、/proc/self/mounts
1.3.2. /proc/self/mountinfo
1.3.3. bind mount
1.3.4. mount namespace简介
1.3.5. docker.sh
1.4. pid namespace
1.4.1. unshare的--fork选项
1.4.2. pid namespace简介
1.4.3. pid嵌套
1.4.4. docker.sh
2. CGroups
2.1. CGroups简介
2.2. 限制内存
2.2.1. 用CGroups限制内存
2.2.2. docker.sh
3. 切换根文件系统
3.1. 根文件系统
3.2. pivot_root
3.3. docker.sh
4. 联合加载
4.1. 联合加载简介
4.2. AUFS
4.3. docker.sh
5. 卷
5.1. 卷简介
5.2. docker.sh
6. 后记Namespace
Namespace简介
传统上,在Linux中,许多资源是全局管理的。例如,系统中的所有进程按照惯例是通过PID标识的,这意味着内核必须管理一个全局的PID列表。而且,所有调用者通过uname系统调用返回的系统相关信息都是相同的。用户id的管理方式类似,即各个用户是通过一个全局唯一的UID标识。
Namespace是Linux用来隔离上述全局资源的一种方式。把一个或多个进程加入到同一个namespace中后,这些进程只会看到该namespace中的资源。namespace是后来加入到Linux中的,为了兼容之前的全局资源管理方式,Linux为每一种资源准备了一个全局的namespace。Linux中的每一个进程都默认加入了这些全局namespace。
Linux中的每个进程都有一个/proc/[pid]/ns/目录,里面包含了该进程所属的namespace信息。我们查看一下当前Shell的/proc/[pid]/ns目录,命令及结果如下:
phl@kernelnewbies:~$ sudo ls -l /proc/$$/ns
total 0
lrwxrwxrwx 1 phl phl 0 Jan 22 08:43 cgroup -> cgroup:[4026531835]
lrwxrwxrwx 1 phl phl 0 Jan 22 08:43 ipc -> ipc:[4026531839]
lrwxrwxrwx 1 phl phl 0 Jan 22 08:43 mnt -> mnt:[4026531840]
lrwxrwxrwx 1 phl phl 0 Jan 22 08:43 net -> net:[4026531993]
lrwxrwxrwx 1 phl phl 0 Jan 22 08:43 pid -> pid:[4026531836]
lrwxrwxrwx 1 phl phl 0 Jan 22 08:43 pid_for_children -> pid:[4026531836]
lrwxrwxrwx 1 phl phl 0 Jan 22 08:43 user -> user:[4026531837]
lrwxrwxrwx 1 phl phl 0 Jan 22 08:43 uts -> uts:[4026531838]该目录下有很多符号链接,每个符号链接代表一个该进程所属的namespace。用readlink读取这些符号链接可以查看进程所属的namespace id。我们读一下当前Shell所属的uts namespace id,命令及结果如下:
phl@kernelnewbies:~$ sudo readlink /proc/$$/ns/uts
uts:[4026531838]后文中我们将介绍uts namespace、mount namespace、pid...
剩余内容已隐藏