docker核心技术

namespace(隔离性)

linux namespace 是一种 linux kernel 提供的资源隔离方案:

  • 系统可以为进程分配不同的 namespace。
  • 保证不同的 namespace 资源独立分配、进程彼此隔离,即不同 namespace 下的进程互不干扰。

linux 内核代码中 namespace 的实现

  • 进程数据结构
struct task_struct {
    ...
    /* namespaces */
    struct nsproxy *nsproxy;
    ...
}

这里 nsproxy 属性就表示这个进程所在的 namespace 的信息。

  • namespace 数据结构
struct nsproxy {
    atomic_t count;
    struct uts_namespace *uts_ns;
    struct ipc_namespace *ipc_ns;
    struct mnt_namespace *mnt_ns;
    struct pid_namespace *pid_ns_for_children;
    struct net *net_ns;
}

linux 对 namespace 的操作方法

  • clone

    在创建新进程的系统调用时,可以通过 flags 参数指定需要新建的 namespace 类型:
    // CLONE_NEWCGROUP, CLONE_NEWIPC, CLONE_NEWNET, CLONE_NEWNS,
    // CLONE_NEWPID, CLONE_NEWUSER, CLONE_NEWUTS

    int clone(int (*fn)(void *), void *child_stack, int flags, void *arg)

  • setns

    该系统调用可以让调用进程加入某个已经存在的 namespace 中:

    int setns(int fd, int nstype)

  • unshare

    该系统调用可以将调用进程移动到新的 namespace 下:

    int unshare(int flags)

关于 namespace 的常用操作

  • 查看当前系统的 namespace:lsns -t <type>
  • 查看某进程的 namespace:ls -la /proc/<pid>/ns/
  • 进入某 namespace 运行命令:nsenter -t <pid> -n ip addr

namespace 练习

  1. 在新的 network namespace 执行 sleep 指令

    unshar -fn sleep 120

  2. 查看进程信息

    ps -ef | grep sleep

    root 476484 476437 0 00:37 pts/3 00:00:00 unshare -fn sleep 120

    root 476485 476484 0 00:37 pts/3 00:00:00 sleep 120

  3. 查看网络 namespace

    lsns -t net

    4026532266 net 2 476484 root unassigned unshare -fn sleep 120

  4. 进入该进程所在 namespace 查看网络配置,与主机不一样

    nsenter -t pid -n ip a

    1: lo: mtu 65536 qdisc noop state DOWN group default qlen 1000
    link/loopback 00:00:00:00:00:00 brd 00:00:00:00:00:00

cgroups(可配额)

Cgroups (control groups) 是 linux 下用于对一个或一组进程进行资源控制和监控的机制。

可以对诸如 CPU 使用时间、内存、磁盘I/O 等进程所需资源进行限制。

不同资源的具体管理工作由相应的 cgroup 子系统来实现。

针对不同类型的资源限制,只要将限制策略在不同的子系统上进行关联即可。

cgroups 在不同的系统资源管理子系统中已层级树(Hierarchy)的方式来组织管理:
每个 cgroup 都可包含其他的子 cgroup,因此子 cgroup 能够使用的资源除了
受本 cgroup 配置的资源参数的限制,还受到父 cgroup 设置的资源限制。

linux 内核代码中 cgroups 的实现

  • 进程数据结构
struct task_struct {
    ...
    #ifdef CONFIG_CGROUPS
    struct css_set __rcu *cgroups;
    struct list_head cg_list;
    #endif
    ...
}

这里 nsproxy 属性就表示这个进程所在的 namespace 的信息。

  • css_set 是 cgroup_subsys_state 对象的集合
struct css_set {
    /*
     * Set of subsystem states, one for each subsystem. This array is
     * immutable after creation apart from the init_css_set during
     * subsystem registration (at boot time).
     */
    struct cgroup_subsys_state *subsys[CGROUP_SUBSYS_COUNT];
}

CPU 子系统

  • cpu.shares:可让出的能获得 CPU 使用时间的相对值。
  • cpu.cfs_period_us:用来配置时间周期长度,单位为 us(微秒)。
  • cpu.cfs_quota_us:用来配置当前 cgroup 在 cfs_period_us 时间内最多能使用的 CPU 时间数,单位为 us(微秒)。
  • cpu.stat:cgroup 内的进程使用的 CPU 时间统计。
  • nr_periods:经过 cfs_period_us 的时间周期数量。
  • nr_throttled:在经过的周期内,由多少次因为进程在指定的时间周期内用光了配额时间而受到限制。
  • throttled_time:cgroup 中的进程被限制使用 CPU 的总用时,单位为 ns(纳秒)。

CPU 子系统练习

  1. 在 cgroup cpu 子系统目录中创建目录结构

    cd /sys/fs/cgroup/cpu
    mkdir cpudemo
    cd cpudemo
    
  2. 运行 busyloop(代码如下)

    package main
    
    func main()  {
        go func() {
            for {}
        }()
        for {}
    }
    
  3. 执行 top 查看 CPU 使用情况,CPU 占 100%(我的ecs只有一核)

  4. 通过 cgroup 限制 CPU 使用

    1. 把进程添加到 cgroup 进程配置组 echo ps -ef | grep busyloop | grep -v grep | awk '{print $2}' > cgroup.procs
    2. 设置 cpuquota echo 10000 > cpu.cfs_quota_us // 每 10 万个 CPU 时间片只能拿到 1 万个
  5. 执行 top 查看 CPU 使用情况,CPU 占用变为 10%

memory 子系统

  • memory.usage_in_bytes:cgroup 下进程使用的内存,包含 cgroup 及其子 cgroup 下的进程使用的内存。
  • memory.max_usage_in_bytes:cgroup 下进程使用内存的最大值,包含子 cgroup 的内存使用量。
  • memory.limit_in_bytes:设置 cgroup 下进程最多能使用的内存。如果设置为 -1,表示对该 cgroup 的内存使用不作限制。
  • memory.oom_control:设置是否在 cgroup 中使用 OOM (Out Of Memory) Killer,默认为使用。
    当属于该 cgroup 的进程使用的内存超过最大的限定值时,会立刻被 OOM Killer 处理。

Union FS

// TODO

  • 8
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值