白話Docker(NameSpace)

Docker容器無(wú)疑是當(dāng)下最火的技術(shù)了。Docker通過(guò)鏡像明確解決的是應(yīng)用打包困難的問(wèn)題燕差。

docker

但是容器本身是沒(méi)有什么價(jià)值的遭笋,有價(jià)值的是容器編排技術(shù)。
容器本身就像一個(gè)沙盒一樣徒探,將應(yīng)用程序打包瓦呼,讓?xiě)?yīng)用程序在沙盒中運(yùn)行,而沙盒中的應(yīng)用程序也能感知到沙盒的邊界测暗,被限制在沙盒之中央串。
Namespace就是修改進(jìn)程視圖的的方法,通過(guò)約束和修改進(jìn)程的動(dòng)態(tài)表現(xiàn)碗啄,從而為其創(chuàng)造一個(gè)“邊界”质和。
Namespace提供了MOUNT,UTS 稚字,IPC侦另,PID,NETWORK尉共,USER的視圖隔離褒傅。

PID Namespace
[root@localhost ~]# docker run -it busybox /bin/sh
/ # ps aux
PID   USER     TIME  COMMAND
    1 root      0:00 /bin/sh
    7 root      0:00 ps aux

可以看到容器內(nèi)部的1號(hào)進(jìn)程是/bin/sh 。而容器內(nèi)一共就只有兩個(gè)進(jìn)程袄友。在容器中執(zhí)行一條語(yǔ)句殿托。

/ # sleep 100000
在容器中 再 docker exec -it xxx /bin/sh 進(jìn)入查看其pid 為 38
/ # ps aux|grep sleep
   38 root      0:00 sleep 100000

而再宿主機(jī)上也有一個(gè)sleep 100000 的進(jìn)程,其pid 為 5181
[root@localhost ~]# ps aux|grep sleep
root       5181  0.0  0.0   1284     4 pts/1    S+   22:23   0:00 sleep 100000

這就是Namespace技術(shù)剧蚣。
其實(shí)這種技術(shù)很早就有了支竹,Linux系統(tǒng)在創(chuàng)建線程的系統(tǒng)調(diào)用 clone() 中指定 CLONE_NEWPID 參數(shù)。

int pid = clone(main_function, stack_size,CLONE_NEWPID|SIGCHLD,NULL)

這就是Linux容器中最底層的實(shí)現(xiàn)了鸠按。
有了PID Namespace 礼搁,可以讓進(jìn)程覺(jué)得自己是 1號(hào)進(jìn)程。有了Mount Namespace目尖,會(huì)讓進(jìn)程只能看到自己的掛載的目錄和文件馒吴。有了Network Namespace,會(huì)讓進(jìn)程只能看到Namespace里的網(wǎng)絡(luò)設(shè)備瑟曲。
所以說(shuō)饮戳,其實(shí)Namespace只是障眼法而已

這樣的障眼法提供了Linux Namespace的隔離性。但是這種隔離性其實(shí)還有很多不足之處洞拨。
  • 容器只是宿主機(jī)上的一種特殊的進(jìn)程扯罐,那么多個(gè)容器之間使用的還是同一個(gè)宿主機(jī)的內(nèi)核。(低版本內(nèi)核的Linux是無(wú)法運(yùn)行高版本內(nèi)核的Linux容器的烦衣,同樣Win的內(nèi)核也運(yùn)行不了Linux容器)
  • 雖說(shuō)已經(jīng)有了很多Namespace歹河。但是時(shí)間是不能被Namespace化的掩浙,容器中調(diào)用了settimeofday()的系統(tǒng)調(diào)用,那么宿主機(jī)也會(huì)被更改秸歧。(盡管有seccomp技術(shù)厨姚,對(duì)容器中的系統(tǒng)調(diào)用有過(guò)濾,但是這會(huì)拖累容器性能寥茫,而且一般也不知道有多少這種坑的系統(tǒng)調(diào)用要被限制)

文件系統(tǒng)的Namespace

進(jìn)到容器后,可以看到容器內(nèi)部有 / 矾麻,也有 /etc 等等纱耻。其實(shí)之前提到了,docker 是方便開(kāi)發(fā)者一次打包多地部署的困難點(diǎn)的险耀,但是最容易忽視的是應(yīng)用程序最大的依賴(lài)不是 jvm或者是 程序庫(kù)弄喘,最大的依賴(lài)應(yīng)該是操作系統(tǒng)本身。如果能將整個(gè)操作系統(tǒng)都打包才是真正解決了打包的困難甩牺。

這里可能想到了 有Mount Namespace 呀蘑志。有了它,容器的應(yīng)用程序里面理應(yīng)看到的是一份完全獨(dú)立的文件系統(tǒng)贬派。這樣就可以在容器中操作容器內(nèi)的目錄(如 /tmp)急但。而不影響宿主機(jī)本身。

下面有一段小程序搞乏,在創(chuàng)建子進(jìn)程時(shí)波桩,開(kāi)啟指定的Namespace。

#define _GNU_SOURCE
#include <sys/mount.h>
#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)
static char container_stack[STACK_SIZE];
char* const container_args[] = {
  "/bin/bash",
  NULL
};

int container_main(void* arg)
{
  printf("Container - inside the container!\n");
  execv(container_args[0], container_args);
  printf("Something's wrong!\n");
  return 1;
}

int main()
{
  printf("Parent - start a container!\n");
  int container_pid = clone(container_main, container_stack+STACK_SIZE, CLONE_NEWNS | SIGCHLD , NULL);
  waitpid(container_pid, NULL, 0);
  printf("Parent - container stopped!\n");
  return 0;
}

這段代碼的功能時(shí)在main函數(shù)中请敦,通過(guò)clone() 系統(tǒng)調(diào)用創(chuàng)建一個(gè)新的子進(jìn)程镐躲,并聲明為它啟用Mount Namespace 。而這個(gè)子進(jìn)程執(zhí)行的是一個(gè) shell侍筛。這個(gè)shell運(yùn)行在 Mount Namespace 隔離環(huán)境中萤皂。

$ ls /tmp

但是執(zhí)行后發(fā)現(xiàn)還是宿主機(jī)的tmp。
其實(shí)不難回答匣椰,光啟用 Namespace 還不行裆熙。因?yàn)檫M(jìn)入容器之后需要重新掛載一次。

int container_main(void* arg)
{
  printf("Container - inside the container!\n");
  // 如果你的機(jī)器的根目錄的掛載類(lèi)型是 shared禽笑,那必須先重新掛載根目錄
  // mount("", "/", NULL, MS_PRIVATE, "");
  mount("none", "/tmp", "tmpfs", 0, "");
  execv(container_args[0], container_args);
  printf("Something's wrong!\n");
  return 1;
}

這時(shí)再執(zhí)行 ls /tmp 弛车。發(fā)現(xiàn) /tmp 為空了。
這就是重新掛載了 /tmp 蒲每。
和其他的Namespace 不一樣纷跛,Mount Namespace 想要生效,必須是伴隨著掛載操作才能生效的
而在 Linux中邀杏,有一個(gè) chroot 的命令贫奠。就是改變進(jìn)程的根目錄到指定的目錄唬血。
而這個(gè)掛載在容器根目錄上,用來(lái)為容器提供隔離后執(zhí)行環(huán)境的文件系統(tǒng)唤崭,就是所謂的“容器鏡像”拷恨,也被稱(chēng)作“rootfs(根文件系統(tǒng))”
所以對(duì)docker來(lái)講。最核心的原理就是為待創(chuàng)建的用戶進(jìn)程

  1. 啟用Linux Namespace配置
  2. 設(shè)置指定的 Cgroups 參數(shù)
  3. 切換進(jìn)程的根目錄(Change root)

還是需要明確一下谢肾。
rootfs 只是一個(gè)操作系統(tǒng)所包含的文件腕侄,配置和目錄,并不包含操作系統(tǒng)的內(nèi)核芦疏。內(nèi)核參數(shù)是一個(gè)全局變量冕杠,一處修改,到處生效酸茴。

由于rootfs 里打包的不只是應(yīng)用分预,而是整個(gè)操作系統(tǒng)的文件和目錄,也就意味著薪捍,應(yīng)用以及它運(yùn)行所需要的所有依賴(lài)笼痹,都被封裝在了一起。

?著作權(quán)歸作者所有,轉(zhuǎn)載或內(nèi)容合作請(qǐng)聯(lián)系作者
  • 序言:七十年代末酪穿,一起剝皮案震驚了整個(gè)濱河市凳干,隨后出現(xiàn)的幾起案子,更是在濱河造成了極大的恐慌被济,老刑警劉巖纺座,帶你破解...
    沈念sama閱讀 218,386評(píng)論 6 506
  • 序言:濱河連續(xù)發(fā)生了三起死亡事件,死亡現(xiàn)場(chǎng)離奇詭異溉潭,居然都是意外死亡净响,警方通過(guò)查閱死者的電腦和手機(jī),發(fā)現(xiàn)死者居然都...
    沈念sama閱讀 93,142評(píng)論 3 394
  • 文/潘曉璐 我一進(jìn)店門(mén)喳瓣,熙熙樓的掌柜王于貴愁眉苦臉地迎上來(lái)馋贤,“玉大人,你說(shuō)我怎么就攤上這事畏陕∨渑遥” “怎么了?”我有些...
    開(kāi)封第一講書(shū)人閱讀 164,704評(píng)論 0 353
  • 文/不壞的土叔 我叫張陵惠毁,是天一觀的道長(zhǎng)犹芹。 經(jīng)常有香客問(wèn)我,道長(zhǎng)鞠绰,這世上最難降的妖魔是什么腰埂? 我笑而不...
    開(kāi)封第一講書(shū)人閱讀 58,702評(píng)論 1 294
  • 正文 為了忘掉前任,我火速辦了婚禮蜈膨,結(jié)果婚禮上屿笼,老公的妹妹穿的比我還像新娘牺荠。我一直安慰自己,他們只是感情好驴一,可當(dāng)我...
    茶點(diǎn)故事閱讀 67,716評(píng)論 6 392
  • 文/花漫 我一把揭開(kāi)白布休雌。 她就那樣靜靜地躺著,像睡著了一般肝断。 火紅的嫁衣襯著肌膚如雪杈曲。 梳的紋絲不亂的頭發(fā)上,一...
    開(kāi)封第一講書(shū)人閱讀 51,573評(píng)論 1 305
  • 那天胸懈,我揣著相機(jī)與錄音担扑,去河邊找鬼。 笑死箫荡,一個(gè)胖子當(dāng)著我的面吹牛魁亦,可吹牛的內(nèi)容都是我干的渔隶。 我是一名探鬼主播羔挡,決...
    沈念sama閱讀 40,314評(píng)論 3 418
  • 文/蒼蘭香墨 我猛地睜開(kāi)眼,長(zhǎng)吁一口氣:“原來(lái)是場(chǎng)噩夢(mèng)啊……” “哼间唉!你這毒婦竟也來(lái)了绞灼?” 一聲冷哼從身側(cè)響起,我...
    開(kāi)封第一講書(shū)人閱讀 39,230評(píng)論 0 276
  • 序言:老撾萬(wàn)榮一對(duì)情侶失蹤呈野,失蹤者是張志新(化名)和其女友劉穎低矮,沒(méi)想到半個(gè)月后,有當(dāng)?shù)厝嗽跇?shù)林里發(fā)現(xiàn)了一具尸體被冒,經(jīng)...
    沈念sama閱讀 45,680評(píng)論 1 314
  • 正文 獨(dú)居荒郊野嶺守林人離奇死亡军掂,尸身上長(zhǎng)有42處帶血的膿包…… 初始之章·張勛 以下內(nèi)容為張勛視角 年9月15日...
    茶點(diǎn)故事閱讀 37,873評(píng)論 3 336
  • 正文 我和宋清朗相戀三年,在試婚紗的時(shí)候發(fā)現(xiàn)自己被綠了昨悼。 大學(xué)時(shí)的朋友給我發(fā)了我未婚夫和他白月光在一起吃飯的照片蝗锥。...
    茶點(diǎn)故事閱讀 39,991評(píng)論 1 348
  • 序言:一個(gè)原本活蹦亂跳的男人離奇死亡,死狀恐怖率触,靈堂內(nèi)的尸體忽然破棺而出终议,到底是詐尸還是另有隱情,我是刑警寧澤葱蝗,帶...
    沈念sama閱讀 35,706評(píng)論 5 346
  • 正文 年R本政府宣布穴张,位于F島的核電站,受9級(jí)特大地震影響两曼,放射性物質(zhì)發(fā)生泄漏皂甘。R本人自食惡果不足惜,卻給世界環(huán)境...
    茶點(diǎn)故事閱讀 41,329評(píng)論 3 330
  • 文/蒙蒙 一悼凑、第九天 我趴在偏房一處隱蔽的房頂上張望叮贩。 院中可真熱鬧击狮,春花似錦、人聲如沸益老。這莊子的主人今日做“春日...
    開(kāi)封第一講書(shū)人閱讀 31,910評(píng)論 0 22
  • 文/蒼蘭香墨 我抬頭看了看天上的太陽(yáng)捺萌。三九已至档冬,卻和暖如春,著一層夾襖步出監(jiān)牢的瞬間桃纯,已是汗流浹背酷誓。 一陣腳步聲響...
    開(kāi)封第一講書(shū)人閱讀 33,038評(píng)論 1 270
  • 我被黑心中介騙來(lái)泰國(guó)打工, 沒(méi)想到剛下飛機(jī)就差點(diǎn)兒被人妖公主榨干…… 1. 我叫王不留态坦,地道東北人盐数。 一個(gè)月前我還...
    沈念sama閱讀 48,158評(píng)論 3 370
  • 正文 我出身青樓,卻偏偏與公主長(zhǎng)得像伞梯,于是被迫代替她去往敵國(guó)和親玫氢。 傳聞我的和親對(duì)象是個(gè)殘疾皇子,可洞房花燭夜當(dāng)晚...
    茶點(diǎn)故事閱讀 44,941評(píng)論 2 355

推薦閱讀更多精彩內(nèi)容