有人的地方就有江湖,IT界也不例外。
在过去几十年里,IT江湖从来都是门派林立,纷争不断。如果按照Operating System (下面简称OS), 大概可以分Windows派,类Unix派,还有苹果派(有没有勾起您的食欲?)。这几大门派信徒众多,教规又各不相同,所以经常造成矛盾。比如说,你要共享一个文件系统,Windows派喜欢用CIFS访问,类Unix派习惯用NFS访问,近年来如日中天的苹果派们则用AFP。为了伺候好这些门派,NAS就需要支持多种共享协议。本文要介绍的,就是类Unix习惯使用的NFS。
NFS的全称是Network File System,即网络文件系统。它使一台电脑可以通过网络访问另外一台电脑上的共享,使用起来就如同本地文件系统一样方便。我在大学里就共享过一整个文件系统,过几天就有校友在上面放了很多小电影,还经常更新。可见共享不仅是奉献,有时候还有收获,感谢共享协议的开发者们!
NFS的开发者就是曾经名震江湖的SUN公司(看名字好像是日月神教的分支),它已经在三年前被甲骨文收入门下。SUN把NFS的第一个版本NFSv1藏在深闺,就像古墓里的小龙女,从不露面。等到在江湖上开始流行NFS,已经是第二版NFSv2了。NFSv2很好用,但是问题也不少,比如它不支持大于2GB的文件,但这在90年代之前还不是大问题。令人费解的是,虽然NFSv3在1995年就面世了,但到今天还有人坚持用NFSv2。我直到写《IT装B指南》时才恍然大悟:用老版本的都是IT贵族啊,配NFSv4的只能算初级iBer。
其实NFS可以工作在任何OS上。只不过因为门派之别,一般只在类Unix环境中使用。目前广泛应用的版本还是NFSv3,我们有机会再另文讨论NFSv4。下图展示了多台客户端通过NFS对NAS的访问。
NAS在这里充当了NFS服务器的角色,而Linux,Solaris和AIX则是NFS客户机。NFS的功能很多,不同的功能对应着不同的daemon。比如一定要有的nfsd和mountd,还有可选的lockd和statd。
每个daemon都需要占用一些端口,但有些daemon是可选的,也许用户根本不会启用它们。所以,NFS并没有给每个NFS daemon保留固定端口(除了nfsd)。而是在系统启动时给需要启用的NFS daemon分配端口,然后把这些端口号告诉RPC daemon。RPC daemon的端口号是固定的111,每个NFS客户机都知道怎么联系它。当客户机需要连接NFS的某个daemon时,就不得不先咨询RPC daemon,获得该NFS daemon对应的端口号,然后再发送NFS请求。
我第一次看到RPC daemon的工作原理,就想起交大管浴室的老头。他的固定地址是门房(相当于端口111),每个要洗澡的学生(NFS客户机)都知道怎么找到他,他会给你一个带号码的钥匙(端口号),有了这个号码,你就可以找到相应的格子(NFS daemon)放衣服了。
很少有人会对自己的共享不加限制,像我一样收获小电影的毕竟是少数,大多数人收获的是恶作剧。NFS通过限制客户机(比如IP地址, hostname等)访问来实现安全控制。下表列举了一些NFS服务器端的参数:
这些配置只能限制一整台客户机,无法限制到具体用户。比如某台客户机被限制为rw,那该机的所有用户都可能有读写权限。这显然是不够安全的,但NFS协议本身又无法识别具体用户的权限。为了解决这个问题,NFS服务器端利用本地权限(rwxrwxrwx,以及owner和group),结合客户端的UID和GID来确定客户端权限。这个机制要求NFS客户机上的User-UID-Group必须都能在服务器上找到,否则容易造成混乱。个人认为NIS是一个很好的选择,我们有机会再另文讨论。
NFS服务器上的共享创建好了之后,客户端就可以挂载(mount)了。挂载的参数很多,我们只介绍对性能影响较大的几个:
挂载之后,我们就可以使用该共享了。我在lab里挂载了一个文件系统(/paddy_fs_01),然后读取其中一个文件(abc.txt)。命令如下:
[root@NISclient ~]# mount 10.32.106.25:/paddy_fs_01 paddy_fs_01
[root@NISclient ~]# cp paddy_fs_01/abc.txt abc.txt
为了更好的说明NFS的工作原理,我把全过程抓了包。把其中不重要的包过滤掉之后,我们可以这样解读(下列序号与截图中的包号相对应):
1. 客户机:RPC,请问nfsd的端口号是多少呀?
2. 服务器:是2049。
3. 客户机:那我测试一下2049通不通。
4. 服务器:收到了,是通的。
5. 客户机:RPC,请问mountd的端口号是多少呀?
6. 服务器:是1234。
7. 客户机:那我测试一下1234通不通。
8. 服务器:收到了,是通的。
9. 客户机:我要挂载 /paddy_fs_01。
10.服务器:(根据该共享的配置,这台客户机有挂载权限,所以)你的请求被批准了。
11.客户机:我测试一下挂上了没有。
12.服务器:挂上了啦。
13.客户机:我想看看这个文件系统的属性。
14.服务器:给,就这些。
...挂载结束,读abc.txt开始:
17. 客户机:我要访问 /paddy_fs_01。
18. 服务器:来吧,(根据你的UID)你有读,查询,更改,扩展和删除的权利。
19. 客户机:我想看看有哪些子目录。
20. 服务器:看,就这些。
21. 客户机:我想看看abc.txt的属性。
22. 服务器:File Mode等属性都在这了。
23. 客户机:我还想再看看。
24. 服务器:再给你一次好了。
25. 客户机:我想访问abc.txt。
26. 服务器:你有权限的,访问吧。
27. 客户机:我要读abc.txt,从0开始读16384字节。
28. 服务器:给。
29. 客户机:我要读abc.txt,从16384开始读32768字节。
(被过滤掉的包,服务器传输32768字节给客户机。)
30. 客户机:我要读abc.txt,从49152开始读32606字节。
(被过滤掉的包,服务器传输32606字节给客户机。)