目标:

快速建立环境用语测试 deb 包安装 / web 应用部署。

可参考 https://github.com/wolf0403/lvmvm 的 README

基础环境:

Ubuntu Natty (11.04) server.

文件系统:

测试环境的快速部署依赖 LVM (Logical Volume Management) 。安装宿主系统方法不限,留足够硬盘创建单一分区,如 /dev/sda5 。

将此分区创建为 LVM 物理卷

pvcreate /dev/sda5

在此分区之上创建 LVM 组

vgcreate data /dev/sda5

创建逻辑分区

lvcreate -n natty /dev/data -L2G

创建 文件系统

mkfs.ext4 /dev/data/natty
创建挂载点并挂载
mkdir /mnt/natty
mount /dev/data/natty /mnt/natty





创建测试环境
debootstrap natty /mnt/natty
完成之后的 /mnt/natty 为一个最基础的 Ubuntu Natty 环境(debootstrap 中可以指定其他版本,如 oneiric 等。将 /mnt/natty 卸载作为范本。

umount /mnt/natty
可以压缩分区以节约磁盘空间:将文件系统减到最小
resize2fs -M /dev/data/natty # 会要求先执行 e2fsck -f /dev/data/natty 等
然后根据文件系统大小相应压缩逻辑卷。$NEW_SIZE 为上一条操作执行后文件系统的大小;应该留有适当余地,否则可能损坏文件系统。或使用 -r 参数。
lvresize -L  $NEW_SIZE /dev/data/natty

创建新测试环境
使用 LVM 的 snapshot 功能创建测试环境:
NEWSIZE=`lvdisplay /dev/data/natty | grep 'Current LE' | egrep -o '[[:digit:]]+'`
VOL=snap1
lvcreate -s /dev/data/natty -n $VOL -l$NEWSIZE
mkdir /mnt/$VOL
mount /dev/data/$VOL /mnt/$VOL
export MP=/mnt/$VOL
touch $MP/chroot.$VOL # 盗梦的陀螺
mount --bind /dev $MP/dev
mount none $MP/dev/pts -t devpts
mount --bind /proc $MP/proc
mount --bind /sys $MP/sys
chroot /mnt/$VOL

网络


此时创建的测试环境虽然文件系统独立,但其他均为共享。如果同时创建多个环境运行网络服务(如 web server 或 fastcgi 等)则可能出现端口冲突。解决方法是通过 veth 给每个环境分配独立的网络。
参考:http://lxc.sourceforge.net/index.php/about/kernel-namespaces/network/configuration/
攻略:
宿主环境打开路由和 arp 代理
 echo 1 > /proc/sys/net/ipv4/ip_forwardecho 1 > /proc/sys/net/ipv4/conf/eth0/proxy_arp
创建虚拟网卡对
ip link add type veth
为网卡对的主机端指定地址。不应与 ethX 冲突
ifconfig veth0 192.168.3.101/24 up
为虚拟网卡打开 arp 转发
echo 1 > /proc/sys/net/ipv4/conf/veth0/proxy_arp
为虚拟网卡对端指定路由(这里 192.168.3.102 是虚拟环境使用的 IP 地址)
route add -host 192.168.3.102 dev veth0
另开一个会话,chroot 进入虚拟环境。用 unshare 命令隔离与宿主的网络空间

unshare -mun chroot /mnt/$VOL
这时执行 ifconfig 应该看不见网卡,ifconfig lo0 可以看见 loopback 网卡,但是没有 IP 地址。在这个 shell 执行
echo $$
得到 PID

在第一个会话中(宿主环境)执行
ip link set veth1 netns $PID
将 veth1 划入虚拟环境

在虚拟环境 chroot shell 中 ifconfig 应该可以看到 veth1 。将 veth1 的地址指定为前述(路由指向的)IP 地址
ifconfig veth1 192.168.3.102

在虚拟环境中测试监听
nc -vv -l 10888
在主机中测试

nc -vv localhost 10888
失败,但
nc -vv 192.168.2.102 10888
成功,说明网络隔离室成功的。

CPU、内存资源

测试利用 cgroups 限定可用内存和 CPU
通过 cgcreate -g memory:Name 创建分组,然后在 /sys/fs/cgroup/memory/Name/memory.limit_in_bytes 中进行设置,如 echo 10M > memory.limit_in_bytes 等。
FIXME: 通过 for (;;) malloc (1024 * 1024) 并未测得相应的结果,内存增长(top 中 VIRT / RES / SHR)与实际占用( /sys/fs/cgroup/Name/memory.usage_in_bytes)并不对应。

问题


Ubuntu 虚拟环境中 MySQL 等脚本无法执行


Ubuntu 8.04 之后的系统启动脚本由 Sysvinit 替换成了 Upstart。Sysvinit 是一组简单的 shell 脚本,由 /sbin/init 创建进程并独立执行,因此相对简单。Ubuntu 使用的 upstart 系统( http://upstart.ubuntu.com )依赖 dbus 通信,因此脚本的执行依赖于 /sbin/init 的执行。而 Ubuntu 的 /sbni/init 又强制要求自己的 PID 为 1,否则直接退出。因为以上的 unshare 命令目前只能处理网络、System V IPC 等名字空间,但是空间仍然是共用的,无法在虚拟环境中正常执行 /sbin/init。


解决方法 1:对于依赖 upstart 的服务,手工启动(如手工执行 mysqld 等)

解决方法 2:利用 LD_PRELOAD 劫持 getpid 返回 1 强制启动虚拟环境的 /sbin/init (http://blog.csdn.net/Wolf0403/article/details/389276)

#include <sys/types.h>
#include <sys/stat.h>
#include <fcntl.h>
#include <dlfcn.h>#include <stdio.h>
#include <stdlib.h>
#include <stdarg.h>pid_t getpid (void) {char *pidstr = getenv ("HJPID");if (pidstr && pidstr[0] == '1' && pidstr[1] == '\0') {return (pid_t) 1;}void *dlh = dlopen ("libc.so.6", RTLD_LAZY);if ( !dlh ) {exit (1);}pid_t (* glibc_getpid) ();glibc_getpid = dlsym ( dlh, "getpid" );if ( ! glibc_getpid ) {exit (2);}pid_t r = glibc_getpid ();dlclose ( dlh );return r;
}

编译


cc -shared -fPIC getpid.c -o libpid.so -ldl

然后用 env LD_PRELOAD=libpid.so HJPID=1 方式插入 /sbin/init 这样可以启动 /sbin/init,但是 MySQL 启动仍然有问题。FIXME



整理


目前测试成功的是在虚拟环境中执行 nginx / php-fcgi,MySQL 可以在 chroot 中执行

相关脚本:https://github.com/wolf0403/lvmvm

关于 PID namespace 的问题,Linux 的 clone(2) 系统调用提供了新的 CLONE_NEWPID 参数用于隔离 PID 名称空间。http://linux.die.net/man/2/clone 可以尝试整合到 unshare 中(TODO)。

资源


Upstart /sbin/init PID = 1: http://linux-vserver.org/Upstart_issues

Linux unshare(1) 命令:http://linux.die.net/man/1/unshare


												

Linux container hand-crafted相关推荐

  1. Linux Container 研究报告

    1. 综述 lxc是Linux Container的用户态工具包.其代码由三部分组成: shell脚本,部分lxc命令是用shell脚本写就的. c语言代码,最终编译成可执行文件.这部分代码也用来提供 ...

  2. 2014 Container技术大会:未来Linux Container会是PaaS平台的核心

    不应错过2014 Container技术大会的九大理由. 一.Docker官方人员再次来到北京,首次向中国布道Docker技术.2013年Docker高级软件工程师Jerome Petazzoni,曾 ...

  3. Arm+linux+container,Container Station和网络虚拟交换机——威联通NAS入门指南(篇四)...

    Container Station和网络虚拟交换机--威联通NAS入门指南(篇四) 2021-01-13 21:14:09 17点赞 105收藏 4评论 哈喽,大家好. 创作声明: 威联通软件容器工作 ...

  4. linux container容器技术框架性理解

    我对container原理的一些理解(基于linux kernel 2.6.38) by kin 2011.04.17 ======================================== ...

  5. 解决 .NET Core 在 Linux Container 中获取 CurrentCulture 不正确的问题

    背景 在将公司一款基于 .NET Framework 的控制台程序迁移到 .NET Core 3.1 时,发现程序中本地化的部分失效,症状类似于对 Thread.CurrentThread.Curre ...

  6. Linux Container(lxc)分析和配置使用

    前提 本文翻译(有道翻译)自linux-container-lxc,根据重点摘录学习. 介绍 最好将容器化定义为:通过操作系统中的特性启用的进程隔离机制. 容器是与系统其他部分隔离的一个或多个进程的集 ...

  7. linux container 原理,容器概念与Linux Container原理

    一.容器与LxC 在像KVM等众多主机虚拟化解决方案中,对每一个虚拟机实例提供的是从底层硬件开始一直到上层的环境,在硬件级进行资源划分.虚拟机的内核是运行在硬件内核之上的.由于每个虚拟实例都有自己的运 ...

  8. linux container框架,理解和配置LinuxContainerExecutor

    最近在研究如何为Hadoop开启基于Kerberos的安全配置,经过千辛万苦配置好后本以为到了见证奇迹的时刻,但是卡在NodeManger无法启动,折磨的死去活来.经历了各种百度.google后依然无 ...

  9. Linux Kernel Namespace实现: namespace API介绍

    1)前言 随着docker的出现, Linux container这种轻量级虚拟化方案越来越在产业里得到大规模的部署和应用. 而Namespace是Linux Container的基础, 了解name ...

最新文章

  1. 自定义编译gdal库
  2. 超云将成为数据中心演化的下一个阶段
  3. mysql无法初始化数据库引擎_mysql使用模板解决旧数据处理,默认初始化数据的通用方法!...
  4. 自定义 URL Scheme 完全指南
  5. CentOS7安装Oracle11g R2全过程
  6. get post put delete在vue中传参方式
  7. 一道经典极限题的分析与求解
  8. Windows Phone开发之路(14) 加载位图
  9. 大型企业***技术(cisco)
  10. matlab波形反白,基于MATLAB的海岸污染物浓度扩散实验分析
  11. Java中string,map,json之间的常用转换方法(json转map,map转json,json转string等)
  12. C语言算法——实现冒泡排序
  13. anti-wrinkle_Anti-wrinkle是什么意思
  14. jumpserver简单安装及使用
  15. eclipse中xtext/xtend的安装及注意事项
  16. 网站防御DDoS的方案--高防节点(高防IP)
  17. python文件和数据格式化思维导图,思维导图:Numpy+Pandas
  18. 输入a,b,c三个整数求其中最大值(C语言实现)
  19. HTML页面刷新方法
  20. python两列时间间隔计算器_在python中有效地比较两列中的每对日期

热门文章

  1. 使用certbot为nginx站点添加免费ssl证书
  2. ANSI、C99、C11 标准区别详解
  3. python实现转置矩阵_用Python转置矩阵?
  4. 简明python教程五----数据结构
  5. 智慧工厂是什么 智慧工厂方案举例 智慧工厂案例
  6. dsp 实验c语言,dsp实验报告 实验1 ccs入门实验2(c语言的使用)
  7. emwin添加图标和图片
  8. eovs实训报告总结心得_实训报告心得体会
  9. 求极值函数-MATLAB
  10. 3、vue-路由、拦截器和嵌套路由