mfs(mooseFS)深入分析(chunkserver选择算法)
2012-04-18 16:08:04

mfs(mooseFS)深入分析(chunkserver选择算法)



数据分布算法是分布式文件系统的核心内容。


mfs是如何选择chunkserver来存储数据是最吸引我的一点,也是我看mfs源码的目的所在。



如果自己设计一套chunkserver选择算法,我们要达到哪些目标呢?


1,文件打散后尽量平均分布到各台chunkserver上


2,各台chunkserver上的chunk数量尽可能的平均


3,数据分发过程衡量系统负载,尽量把数据放在负载低的chunkserver上


4,数据分发过程是否应该衡量各台chunkserver的可用空间???


5,机架感应???



回到mfs上,我们来看看它的分布算法。


还记得matocsserventry结构中的carry字段么,这个字段就是分布算法的核心。


每台chunkserver会有自己的carry值,在选择chunkserver会将每台chunkserver按照carry从大到小做快速排序,


优先选择carry值大的chunkserver来使用。



在描述具体算法前,先介绍三个概念:


allcnt:mfs中可用的chunkserver的个数


availcnt:mfs中当前可以直接存储数据的chunkserver的个数


demand:当前文件的副本数目



先说allcnt,可用的chunkserver要满足下面几个条件:


1,chunkserver是活着的


2,chunkserver的总空间大于0


3,chunkserver的可用空间(总空间-使用空间)大于1G



availcnt指的是carry值大于1的可用chunkserver的个数,也就是在allcnt的约束条件上加一条carry值大于1。



文件1.txt需要存储2个副本,但是mfs中仅仅有1台chunkserver可用,也就是demand>allcnt的时候,


mfs会自动减少文件的副本个数到allcnt,保证文件可以成功写入系统。



关于carry有下面几个规则:


1,仅carry值大于1的chunkserver可以存储新数据


2,每台chunkserver存储新数据后其carry会减1


3,demand>availcnt的时候,会递归的增加每台chunkserver的carry值,直到demand<=availcnt为止


4,每台chunkserver每次carry值的增加量等于当前chunkserver总空间除以最大的chunkserver总空间



上面的规则比较复杂,举个例子就更加清晰了。



chunkserver 1:totalspace:3.94G carry:0.463254


chunkserver 2:totalspace:7.87G carry:0.885674



文件1.txt大小1k,mfs默认一个chunk大小为64M,所以仅仅需要一个chunk就够了。



此时 availcnt=0,demand=1,所以需要增加carry值



chunkserver 1:carry=0.463254 + (3.94/7.87) = 0.463254 + 0.500005 = 0.963259


chunkserver 2:carry=0.885674 + (7.87/7.87) = 0.885674 + 1.000000 = 1.885674



此时 availcnt=1,demand=1,所以不需要增加carry值


对chunkserver按照carry从大到小排序结果为:chunkserver 2 > chunkserver 1


文件1.txt的chunk会存储到chunkserver 2上,同时chunkserver 2的carry会减1


如下:



chunkserver 1:carry=0.963259


chunkserver 2:carry=1.885674 – 1 = 0.885674



文件2.txt大小1k,mfs默认一个chunk大小为64M,所以仅仅需要一个chunk就够了。



此时 availcnt=0,demand=1,所以需要增加carry值



chunkserver 1:carry=0.963259 + (3.94/7.87) = 0.963259 + 0.500005 = 1.463264


chunkserver 2:carry=0.885674 + (7.87/7.87) = 0.885674 + 1.000000 = 1.885674



此时 availcnt=2,demand=1,所以不需要增加carry值


对chunkserver按照carry从大到小排序结果为:chunkserver 2 > chunkserver 1


文件2.txt的chunk会存储到chunkserver 2上,同时chunkserver 2的carry会减1


如下:



chunkserver 1:carry=1.463264


chunkserver 2:carry=1.885674 – 1 = 0.885674



文件3.txt大小1k,mfs默认一个chunk大小为64M,所以仅仅需要一个chunk就够了。



此时 availcnt=1,demand=1,所以不需要增加carry值


对chunkserver按照carry从大到小排序结果为:chunkserver 1 > chunkserver 2


文件3.txt的chunk会存储到chunkserver 1上,同时chunkserver 1的carry会减1


如下:



chunkserver 1:carry=1.463264 – 1 = 0.463264


chunkserver 2:carry=0.885674



因为两台chunkserver的总空间大小不一致,根据算法总空间大的那台chunkserver会存储更多的新数据。


记住,仅仅和chunkserver的总空间有关系,和可用空间没有任何关系。


也就是说,当各台chunkserver总空间大小差不多的情况下,chunk能更好的平均分布,否则mfs会更倾向于选择总空间大的机器来使用。



最后一个问题,当mfs刚刚启动的时候,carry值是如果获得的?


答案是随机产生,通过rndu32()这个函数,随机产生一个小于1,大于等于0的数。


测试结果如下:


Nov 23 01:01:25 sunwg mfsmaster[13175]: 192.168.0.159,0.594834


Nov 23 01:01:25 sunwg mfsmaster[13175]: 192.168.0.160,0.000000



Nov 23 01:03:58 sunwg mfsmaster[13187]: 192.168.0.159,0.516242


Nov 23 01:03:58 sunwg mfsmaster[13187]: 192.168.0.160,0.826559



Nov 23 01:04:17 sunwg mfsmaster[13192]: 192.168.0.159,0.123765


Nov 23 01:04:17 sunwg mfsmaster[13192]: 192.168.0.160,0.389592


><