Linux命名空间学习教程(二) IPC

简介: 本文讲的是Linux命名空间学习教程(二) IPC,【编者的话】Docker核心解决的问题是利用LXC来实现类似VM的功能,从而利用更加节省的硬件资源提供给用户更多的计算资源。而 LXC所实现的隔离性主要是来自内核的命名空间, 其中pid、net、ipc、mnt、uts 等命名空间将容器的进程、网络、消息、文件系统和hostname 隔离开。
本文讲的是Linux命名空间学习教程(二) IPC 【编者的话】Docker核心解决的问题是利用LXC来实现类似VM的功能,从而利用更加节省的硬件资源提供给用户更多的计算资源。而 LXC所实现的隔离性主要是来自内核的命名空间, 其中pid、net、ipc、mnt、uts 等命名空间将容器的进程、网络、消息、文件系统和hostname 隔离开。本文是Linux命名空间系列教程的第二篇,重点介绍了IPC命名空间。DockerOne在 撸代码 的基础上进行了校对和整理。

继上一篇  关于UTS namespace的文章 (hostname隔离),我们将继续学习面向安全的namespace:IPC(Inter-Process Communications,进程间通信)。如果你尚未阅读UTS部分,我强烈建议你先阅读这个系列的 第一篇文章 ,了解一下linux namespace的隔离机制。

要激活IPC namespace,只需要把“CLONE_NEWPIC”标记添加到“clone”的调用中,而不需要其它额外的步骤。IPC namespace也能和其他namespace组合使用。

一旦激活,你将能够如同往常一样创建IPC,甚至是命名一个,并且不会与其他任何应用冲突。

但是,请先等一下!我的“父进程”和“子进程”现在不是隔离的吗?那么如果我需要让它们通信,应该如何解决这一问题?

好问题,一个常规方案是在child全权控制之前,在parent中增加一些额外的步骤。幸运的是,并非所有的东西都是隔离的,clone和它的parent分享内存空间,因此你依旧可以使用:
  • 信号(signal)
  • poll内存
  • 套接字(sockets)
  • 使用文件(file)和文件描述符(fd)

由于上下文(context)的改变,使用signal也许不是最佳方案。而使用poll memory来做通信则太TM低效了!

如果你并不计划完全隔离网络栈,你可以使用sockets,而文件系统也是类似。但是,在这个系列的例子里,这正是我们要做的事: 一步步隔离一切

一个鲜有人知/鲜有人用的方案是监视一对pipe上的事件。事实上,这是Lennart Poettering在 Systemd's "nspawn" 中使用过的技术。我会在这里引入这种极其强大的技术。这也正是我们在下一篇文章中所依赖的技术。

首先,我们需要初始化一对pipe。让我们称之为“检查点”。
checkpoint-global-init.c
// required headers:

include <unistd.h>

// global status:
int checkpoint[2];
// [parent] init:
pipe(checkpoint);

这里的思想是,在parent中触发一个“close”事件,并且在child的读取端等待“EOF”被接收。当EOF被接收后,所有写fd的文件必须被关闭,这是我们需要理解的最重要的东西。因此,在child等待前,应先关闭我们写fd的副本。
checkpoint-child-init.c
// required headers:

include <unistd.h>

// [child] init:
close(checkpoint[1]);

现在,“信号”是很直接的:
1. 在parent中关闭写fd
2. 在child中等待EOF

checkpoint-signal.c
// required headers:

include <unistd.h>

// [child] wait:
char c; // stub char
read(checkpoint[0], &amp;c, 1);
// [parent] signal ready code:
close(checkpoint[1]);


如果我们将它和第一个例子中的UTS namespace放在一起,将是如下样子:
main-2-ipc.c
 
 

define _GNU_SOURCE

include <sys/types.h>

include <sys/wait.h>

include <stdio.h>

include <sched.h>

include <signal.h>

include <unistd.h>

define STACK_SIZE (1024 * 1024)

// sync primitive int checkpoint[2]; static char child_stack[STACK_SIZE]; char* const child_args[] = { "/bin/bash", NULL }; int child_main(void* arg) { char c; // init sync primitive close(checkpoint[1]); // wait... read(checkpoint[0], &c, 1); printf(" - World !\n"); sethostname("In Namespace", 12); execv(child_args[0], child_args); printf("Ooops\n"); return 1; }  int main() { // init sync primitive pipe(checkpoint); printf(" - Hello ?\n"); int child_pid = clone(child_main, child_stack+STACK_SIZE,   CLONE_NEWUTS | CLONE_NEWIPC | SIGCHLD, NULL); // some damn long init job sleep(4); // signal "done" close(checkpoint[1]); waitpid(child_pid, NULL, 0); return 0; }
由于需要高级特性,我们需要root或者对等的权限来运行这段代码。很显然,没有必要在这个例子中保留“CLONE_NEWUTS”。我保留它仅仅是为了展示多个namespace也许可以一起使用。

这就是IPC的所有东西,它本身并不复杂。正如我们接下来要做的,它只有在parent/child同步时才变得复杂,而这正需要“pipe”技术来作为一个方便的解决方案。产品中已经使用了这个技术。

下一篇,是我(作为系统管理员)最喜欢的部分:PID namespaces。

原文链接:Introduction to Linux namespaces – Part 2: IPC(翻译:孙科 审校:李颖杰)

原文发布时间为:2014-12-25
本文作者:codesun
本文来自云栖社区合作伙伴DockerOne,了解相关信息可以关注DockerOne。
原文标题:Linux命名空间学习教程(二) IPC
目录
相关文章
|
19天前
|
Linux
linux下搭建tftp服务器教程
在Linux中搭建TFTP服务器,需安装`tftp-server`(如`tftpd-hpa`)。步骤包括:更新软件包列表,安装`tftpd-hpa`,启动并设置开机自启,配置服务器(编辑`/etc/default/tftpd-hpa`),添加选项,然后重启服务。完成后,可用`tftp`命令进行文件传输。例如,从IP`192.168.1.100`下载`file.txt`: ``` tftp 192.168.1.100 &lt;&lt;EOF binary put file.txt quit EOF ```
28 4
|
1月前
|
网络协议 Shell Linux
【Shell 命令集合 网络通讯 】Linux 设置和配置PPP pppsetup命令 使用教程
【Shell 命令集合 网络通讯 】Linux 设置和配置PPP pppsetup命令 使用教程
42 0
|
1月前
|
网络协议 Shell Linux
【Shell 命令集合 网络通讯 】Linux 创建网络连接 nc命令 使用教程
【Shell 命令集合 网络通讯 】Linux 创建网络连接 nc命令 使用教程
37 1
|
1月前
|
缓存 网络协议 Linux
【Shell 命令集合 网络通讯 】Linux 配置DNS dnsconf 命令 使用教程
【Shell 命令集合 网络通讯 】Linux 配置DNS dnsconf 命令 使用教程
38 0
|
3天前
|
Unix Linux Windows
Linux的学习之路:3、基础指令(2)
Linux的学习之路:3、基础指令(2)
25 0
|
2天前
|
消息中间件 Unix Linux
Linux的学习之路:17、进程间通信(1)
Linux的学习之路:17、进程间通信(1)
17 1
|
2天前
|
存储 安全 Linux
Linux的学习之路:9、冯诺依曼与进程(1)
Linux的学习之路:9、冯诺依曼与进程(1)
18 0
|
17天前
|
Linux 应用服务中间件 网络安全
小白学习Linux的学习建议和阶段
【4月更文挑战第5天】小白学习Linux的学习建议和阶段
46 0
|
28天前
|
消息中间件 Linux 开发工具
Linux系统安装RabbitMQ详细教程
Linux系统安装RabbitMQ详细教程
21 0
|
29天前
|
消息中间件 存储 网络协议
Linux IPC 进程间通讯方式的深入对比与分析和权衡
Linux IPC 进程间通讯方式的深入对比与分析和权衡
69 0