docker cp 命令的底层实现原理
docker 文件系统
OverlayFS是一种堆叠文件系统,将原来底层文件系统中不同的目录进行“合并”,然后向用户呈现。

具体解释如下:
1) lower dirA / lower dirB目录和upper dir目录为来自底层文件系统的不同目录,内部包含了想要合并的文件和目录
2) merge dir目录为挂载点。当文件系统挂载后,在merge目录下将会同时看到来自各lower和upper目录下的内容,并且用户也无法(无需)感知这些文件分别哪些来自lower dir,哪些来自upper dir,用户看见的只是一个普通的文件系统根目录而已(lower dir可以有多个也可以只有一个)。
3)当upper dir和lower dir两个目录存在同名文件时,lower dir的文件将会被隐藏,用户只能看见来自upper dir的文件,然后各个lower dir也存在相同的层次关系,较上层屏蔽下层的同名文件。除此之外,如果存在同名的目录,那就继续合并(lower dir和upper dir合并到挂载点目录其实就是合并一个典型的例子)。
4)各层目录中的upper dir是可读写的目录,当用户通过merge dir向其中一个来自upper dir的文件写入数据时,那数据将直接写入upper dir下原来的文件中,删除文件也是同理;
5)而各lower dir则是只读的,在overlayfs挂载后无论如何操作merge目录中对应来自lower dir的文件或目录,lower dir中的内容均不会发生任何的改变。当用户想要往来自lower层的文件添加或修改内容时,overlayfs首先会的拷贝一份lower dir中的文件副本到upper dir中,后续的写入和修改操作将会在upper dir下的copy-up的副本文件中进行,lower dir原文件被隐藏。
总结:(1)上下层同名目录合并;(2)上下层同名文件覆盖;(3)lower dir文件写时拷贝。这三点对用户都是不感知的。
docker 实现文件隔离的方法
1) 启用Linux Namespace配置
启用Mount Namespace(即:CLONE_NEWNS标志), 进程运行在了Mount Namespace的隔离环境中。
2) 切换进程的根目录(Change Root)
chroot(change root file system) 命令, 改变进程的根目录到指定的位置, 在经过 chroot 之后,在新根目录下将访问不到旧系统的根目录结构和文件
docker cp 时发生的事情
为将文件从容器中拷出,Docker使用了一个辅助进程:docker-tar, docker-tar的原理是chroot到容器,归档其中请求的文件及目录,然后将生成的tar文件传回Docker守护进程,该进程负责将文件提取到宿主机上的目标目录中。执行chroot操作最主要的目的是避免符号链接(symlink)攻击,当宿主机进程尝试访问容器中的文件时就可能发生这种攻击。如果其中某个文件为符号链接,那么就可能被解析到宿主机的根目录,这样攻击者控制的容器就有可能通过容器的cp命令在宿主机上读取并写入文件。