The.Google.File.System自编中文打印版.pdf
- 文档编号:3433391
- 上传时间:2023-05-05
- 格式:PDF
- 页数:32
- 大小:768.73KB
The.Google.File.System自编中文打印版.pdf
《The.Google.File.System自编中文打印版.pdf》由会员分享,可在线阅读,更多相关《The.Google.File.System自编中文打印版.pdf(32页珍藏版)》请在冰点文库上搜索。
?
第1页TheGoogleFileSystemSanjayGhemawat,HowardGobioff,andShun-TakLeungGooglesanjay,hgobioff,CopyrightPermissiontomakedigitalorhardcopiesofallorpartofthisworkforpersonalorclassroomuseisgrantedwithoutfeeprovidedthatcopiesarenotmadeordistributedforprofitorcommercialadvantageandthatcopiesbearthisnoticeandthefullcitationonthefirstpage.Tocopyotherwise,torepublish,topostonserversortoredistributetolists,requirespriorspecificpermissionand/orafee.SOSP03,October1922,2003,BoltonLanding,NewYork,USA.Copyright2003ACM1-58113-757-5/03/0010.$5.00.摘要我们已经设计和实现了GoogleFileSystem,一个适用于大规模分布式数据处理相关应用的,可扩展的分布式文件系统。
它基于普通的不算昂贵的硬件设备,实现了容错的设计,并且为大量客户端提供极高的聚合处理性能。
我们的设计目标和上一个版本的分布式文件系统有很多相同的地方,我们的设计是依据我们应用的工作量以及技术环境来设计的,包括现在和预期的,都有一部分和早先的文件系统的约定有所不同。
这就要求我们重新审视传统的设计选择,以及探索究极的设计要点。
这个文件系统正好与我们的存储要求相匹配。
这个文件系统在Google内部广泛应用于作为存储平台使用,适用于我们的服务要求产生和处理数据应用,以及我们的研发要求的海量数据的要求。
最大的集群通过上千个计算机的数千个硬盘,提供了数百TB的存储,并且这些数据被数百个客户端并行同时操作。
在这个论文里,我们展示了用于支持分布式应用的扩展文件系统接口设计,讨论了许多我们设计的方面,并且列出了我们的micro-benchmarks以及真实应用性能指标。
分类和主题描述D4:
3分布式文件系统?
第2页普通条目设计,可靠性,性能,测量Design,reliability,performance,measurement关键词容错,扩展性,数据存储,集群数据存储1介绍我们已经为Google迅速增长的数据处理需要而设计和实现了GoogleFileSystem(GFS)。
GFS和上一个分布式文件系统有着很多相同的设计目标,比如性能,扩展性,可靠性,以及可用性。
不过,他的设计是基于我们应用的工作量和技术环境驱动的,包括现在和预期的,都有部分和上一个版本的约定有点不同。
这就要求我们重新审视传统的设计选择,以及探索究极的设计要点。
首先,节点失效将被看成是正常情况,而不再视为异常情况。
整个文件系统包含了几百个或者几千个由廉价的普通机器组成的存储机器,而且这些机器是被与之匹配数量的客户端机器访问。
这些节点的质量和数量都实际上都确定了在任意给定时间上,一定有一些会处于失效状态,并且某一些并不会从当前失效中恢复回来。
这有可能由于程序的bug,操作系统的bug,人工操作的失误,以及硬盘坏掉,内存,网络,插板的损坏,电源的坏掉等等。
因此,持续监视,错误检测,容错处理,自动恢复必须集成到这个文件系统的设计中来。
其次,按照传统标准来看,文件都是非常巨大的。
数个GB的文件是常事。
每一个文件都包含了很多应用程序对象,比如web文档等等。
当我们通常操作迅速增长的,由很多TB组成的,包含数十亿对象的数据集,我们可不希望管理数十亿个KB大小的文件,即使文件系统能支持也不希望。
所以,设计约定和设计参数比如I/O操作以及blocksize(块大小),都需要重新审查。
第三,大部分文件都是只会在文件尾新增加数据,而少见修改已有数据的。
对一个文件的随机写操作在实际上几乎是不存在的。
当一旦写完,文件就是只读的,并且一般都是顺序读取得。
多种数据都是有这样的特性的。
有些数据可能组成很大的数据仓库,并且数据分析程序从头扫描到尾。
有些可能是运行应用而不断的产生的数据流。
有些是归档的数据。
有些是一个机器为另一个机器产生的中间结果,另一个机器及时或者随后处理这些中间结果。
对于这些巨型文件的访问模式来说,增加模式是最重要的,所以我们首要优化性能的以及原子操作保证的就是它,而在客户端cache数据块没有什么价值。
第四,与应用一起设计的的文件系统API对于增加整个系统的弹性适用性有很大的好处。
例如我们不用部署复杂的应用系统就可以把GFS应用到大量的简单文件系统基础上。
我们也引入了原子的增加操作,这样可以让多个客户端同时操作一个文件,而不需要他们之间有额外的同步操作。
这些在本论文的后边章节有描述。
?
第3页多个GFS集群现在是作为不同应用目的部署的。
最大的一个有超过1000个存储节点,超过300TB的硬盘存储,并且负担了持续沉重的上百个在不同机器上的客户端的访问。
2设计概览2.1约定在为我们的需要设计文件系统得时候,我们需要建立的事先约定同时具有挑战和机遇。
我们早先提到的关于观测到的关键要点,现在详细用约定来说明。
?
系统是建立在大量廉价的普通计算机上,这些计算机经常故障。
必须对这些计算机持续进行检测,并且在系统的基础上进行:
检查,容错,以及从故障中进行恢复。
?
系统存储了大量的超大文件。
我们与其有好几百万个文件,每一个超过100MB。
数GB的文件经常出现并且应当对大文件进行有效的管理。
同时必须支持小型文件,但是我们不必为小型文件进行特别的优化。
?
一般的工作都是由两类读取组成:
大的流式读取和小规模的随机读取。
在大的流式读取中,每个读操作通常要读取几百k的数据,每次读取1M或者以上的数据也很常见。
对于同一个客户端来说,往往会发起连续的读取操作顺序读取一个文件。
小规模的随机读取通常在文件的不同位置,读取几k数据。
对于性能有过特别考虑的应用通常会作批处理并且对他们读取的内容进行排序,这样可以使得他们的读取始终是单向顺序读取,而不需要往回读取数据。
?
通常基于GFS的操作都有很多超大的,顺序写入的文件操作。
通常写入操作的数据量和杜如的数据量相当。
一旦完成写入,文件就很少会更改。
对于文件的随机小规模写入是要被支持的,但是不需要为此作特别的优化。
?
系统必须非常有效的,明确细节的对多客户端并行添加同一个文件进行支持。
我们的文件经常使用生产者/消费者队列模式,或者作为多路合并模式进行操作。
好几百个运行在不同机器上的生产者,将会并行增加一个文件。
其本质就是最小的原子操作的定义。
读取操作可能接着生产者操作进行,消费者会同时读取这个文件。
?
高性能的稳定带宽的网络要比低延时更加重要。
我们的目标应用程序一般会大量操作处理比较大块的数据,并且很少有应用要求某个读取或者写入要有一个很短的响应时间。
2.2接口GFS提供了常见的文件系统的接口,虽然他没有实现一些标准的API比如POSIX。
文件是通过pathname来通过目录进行分层管理的。
我们支持的一些常见操作:
create,delete,open,close,read,write等文件操作。
?
第4页另外,GFS有snapshot,recordappend等操作。
snapshort创建一个文件或者一个目录树的快照,这个快照的耗费比较低。
recordappend允许很多个客户端同时对一个文件增加数据,同时保证每一个客户端的添加操作的原子操作性。
这个对于多路合并操作和多个客户端同时操作的生产者/消费者队列的实现非常有用,它不用额外的加锁处理。
这种文件对于构造大型分布式应用来说,是不可或缺的。
snapshot和recordappend在后边的3.4和3.3节有单独讲述。
2.3架构GFS集群由一个单个的master和好多个chunkserver(块服务器)组成,GFS集群会有很多客户端client访问(图1)。
每一个节点都是一个普通的Linux计算机,运行的是一个用户级别(user-level)的服务器进程。
只要机器资源允许,并且允许不稳定的应用代码导致的低可靠性,我们就可以运行chunkserver和client可以运行在同一个机器上。
在GFS下,每一个文件都拆成固定大小的chunk(块)。
每一个块都由master根据块创建的时间产生一个全局唯一的以后不会改变的64位的chunkhandle标志。
chunkservers在本地磁盘上用Linux文件系统保存这些块,并且根据chunkhandle和字节区间,通过LInux文件系统读写这些块的数据。
出于可靠性的考虑,每一个块都会在不同的chunkserver上保存备份。
缺省情况下,我们保存3个备份,不过用户对于不同的文件namespace区域,指定不同的复制级别。
master负责管理所有的文件系统的元数据。
包括namespace,访问控制信息,文件到chunk的映射关系,当前chunk的位置等等信息。
master也同样控制系统级别的活动,比如chunk的分配管理,孤点chunk的垃圾回收机制,chunkserver之间的chunk镜像管理。
master和这些chunkserver之间会有定期的心跳线进行通讯,并且心跳线传递信息和chunckserver的状态。
连接到各个应用系统的GFS客户端代码包含了文件系统的API,并且会和master和chunkserver进行通讯处理,代表应用程序进行读写数据的操作。
客户端和master进行元数据的操作,但是所有的数据相关的通讯是直接和chunkserver进行的。
我们并没有提供POSIXAPI并且不需要和LInux的vnode层相关。
客户端或者chunkserver都不会cache文件数据。
客户端cache机制没啥用处,这是因为大部分的应用都是流式访问超大文件或者操作的数据集太大而不能被chache。
不设计cache系统使得客户端以及整个系统都大大简化了(少了cache的同步机制)(不过客户端cache元数据)。
chunkserver不需要cache文件数据,因为chunks就像本地文件一样的被保存,所以LInux的buffercache已经把常用的数据cache到了内存里。
2.4单个master?
第5页引入一个单个master的设计可以大大简化我们的设计,并且也让master能够基于全局的角度来管理chunk的存放和作出复制决定。
不过,我们必须尽量减少master的读和写操作,以避免它成为瓶颈。
客户端永远不会通过master来做文件的数据读写。
客户端只是问master它应当访问那一个chunkserver来访问数据。
客户端在一定时间内cache这个信息,并且在后续的操作中都直接和chunkserver进行操作。
这里我们简单介绍一下图1中的读取操作。
首先,客户端把应用要读取的文件名和偏移量,根据固定的chunk大小,转换成为文件的chunkindex。
然后向master发送这个包含了文件名和chunkindex的请求。
master返回相关的chunkhandle以及对应的位置。
客户端cache这些信息,把文件名和chunkindex作为cache的关键索引字。
于是这个客户端就像对应的位置的chunkserver发起请求,通常这个会是离这个客户端最近的一个。
请求给定了chunkhandle以及一个在这个chunk内需要读取得字节区间。
在这个chunk内,再次操作数据将不用再通过客户端-master的交互,除非这个客户端本身的cache信息过期了,或者这个文件重新打开了。
实际上,客户端通常都会在请求中附加向master询问多个chunk的信息,master于是接着会立刻给这个客户端回应这些chunk的信息。
这个附加信息是通过几个几乎没有任何代价的客户端-master的交互完成的。
2.5chunk块大小chunk的大小是一个设计的关键参数。
我们选择这个大小为64M,远远大于典型的文件系统的block大小。
每一个chunk的实例(复制品)都是作为在chunkserver上的Linux文件格式存放的,并且只有当需要的情况下才会增长。
滞后分配空间的机制可以通过文件内部分段来避免空间浪费,对于这样大的chunksize来说,(内部分段fragment)这可能是一个最大的缺陷了。
选择一个很大的chunk大小提供了一些重要的好处。
首先,它减少了客户端和master的交互,因为在同一个chunk内的读写操作之需要客户端初始询问一次master关于chunk位置信息就可以了。
这个减少访问量对于我们的系统来说是很显著的,因为我们的应用大部分是顺序读写超大文件的。
即使是对小范围的随机读,?
第6页客户端可以很容易cache一个好几个TB数据文件的所有的位置信息。
其次,由于是使用一个大的chunk,客户端可以在一个chunk上完成更多的操作,它可以通过维持一个到chunkserver的TCP长连接来减少网络管理量。
第三,它减少了元数据在master上的大小。
这个使得我们可以把元数据保存在内存,这样带来一些其他的好处,详细请见2.6.1节。
在另一方面,选择一个大型的chunk,就算是采用滞后分配空间的模式,也有它的不好的地方。
小型文件包含较少树木的chunk,也许只有一个chunk。
保存这些文件的chunkserver就会在大量客户端访问的时候就会成为焦点。
在实践中,焦点问题不太重要因为我们的应用大部分都是读取超大的文件,顺序读取超多的chunk的文件的。
不过,随着batch-queue系统开始使用GFS系统的时候,焦点问题就显现出来了:
一个可执行的程序在GFS上保存成为一个单chunk的文件,并且在数百台机器上一起启动的时候就出现焦点问题。
只有两三个chunkserver保存这个可执行的文件,但是有好几百台机器一起请求加载这个文件导致系统局部过载。
我们通过把这样的执行文件保存份数增加,以及错开batchqueue系统的各worker启动时间来解决这样的问题。
一劳永逸的解决方法是让客户端能够互相读取数据,这样才是解决之道。
2.6元数据master节点保存这样三个主要类型的数据:
文件和chunk的namespace,文件到chunks的映射关系,每一个chunk的副本的位置。
所有的元数据都是保存在master的内存里的。
头两个类型(namepspaces和文件到chunk的映射)同时也是由在master本地硬盘的记录所有变化信息的operationlog来持久化保存的,这个记录也会在远端机器上保存副本。
通过log,在master宕机的时候,我们可以简单,可靠的恢复master的状态。
master并不持久化保存chunk位置信息。
相反,他在启动地时候以及chunkserver加入集群的时候,向每一个chunkserver询问他的chunk信息。
2.6.1内存数据结构因为元数据都是在内存保存的,master的操作很快。
另外master也很容易定时后台扫描所有的内部状态。
定时内部状态扫描是用于实现chunk的垃圾回收机制,当chunkserver失效的时候重新复制,以及为了负载均衡和磁盘空间均衡使用的目的做chunkserver之间的chunk镜像。
4.3和4.4节将讨论这些操作的细节。
这种内存保存数据的方式有一个潜在的问题,就是说整个系统的chunk数量以及对应的系统容量是受到master机器的内存限制的。
这个在实际生产中并不是一个很重要的限制。
master为每64Mchunk分配的空间不到64个字节的元数据。
大部分的chunks都是装满了的,因为大部分文件都是很大的,包含很多个chunk,只有文件的最后部分可能是有空间的。
类似的,文件的名字空间通常对于每一个文件来说要求少于64个字节,因为保存文件名的时候是使用前缀压缩的机制。
如果有需要支持到更大的文件系统,因为我们是采用内存保存元数据的方式,所以我们可以很简单,可靠,高效,灵活的通过增加master机器的内存就可以了。
?
第7页2.6.2chunk的位置master并不持久化保存chunkserver上保存的chunk的记录。
它只是在启动的时候简单的从chunkserver取得这些信息。
master可以在启动之后一直保持自己的这些信息是最新的,因为它控制所有的chunk的位置,并且使用普通心跳信息监视chunkserver的状态。
我们最开始尝试想把chunk位置信息持久化保存在master上,但是我们后来发现如果再启动时候,以及定期性从chunkserver上读取chunk位置信息会使得设计简化很多。
因为这样可以消除master和chunkserver之间进行chunk信息的同步问题,当chunkserver加入和离开集群,更改名字,失效,重新启动等等时候,如果master上要求保存chunk信息,那么就会存在信息同步的问题。
在一个数百台机器的组成的集群中,这样的发生chunserver的变动实在是太平常了。
此外,不在master上保存chunk位置信息的一个重要原因是因为只有chunkserver对于chunk到底在不在自己机器上有着最后的话语权。
另外,在master上保存这个信息也是没有必要的,因为有很多原因可以导致chunserver可能忽然就丢失了这个chunk(比如磁盘坏掉了等等),或者chunkserver忽然改了名字,那么master上保存这个资料啥用处也没有。
2.6.3操作记录(operationlog)操作记录保存了关键的元数据变化历史记录。
它是GFS的核心。
不仅仅因为这时唯一持久化的元数据记录,而且也是因为操作记录也是作为逻辑时间基线,定义了并行操作的顺序。
chunks以及文件,连同他们的版本(参见4.5节),都是用他们创建时刻的逻辑时间基线来作为唯一的并且永远唯一的标志。
由于操作记录是极关键的,我们必须可靠保存之,在元数据改变并且持久化之前,对于客户端来说都是不可见的(也就是说保证原子性)。
否则,就算是chunkserver完好的情况下,我们也可能会丢失整个文件系统,或者最近的客户端操作。
因此,我们把这个文件保存在多个不同的主机上,并且只有当刷新这个相关的操作记录到本地和远程磁盘之后,才会给客户端操作应答。
master可以每次刷新一批日志记录,以减少刷新和复制这个日志导致的系统吞吐量。
master通过自己的操作记录进行自身文件系统状态的反演。
为了减少启动时间,我们必须尽量减少操作日志的大小。
master在日志增长超过某一个大小的时候,执行checkpoint动作,卸出自己的状态,这样可以使下次启动的时候从本地硬盘读出这个最新的checkpoint,然后反演有限记录数。
checkpoint是一个类似B-树的格式,可以直接映射到内存,而不需要额外的分析。
这更进一步加快了恢复的速度,提高了可用性。
因为建立一个checkpoint可能会花一点时间,于是我们这样设定master的内部状态,就是说新建立的checkpoint可以不阻塞新的状态变化。
master切换到一个新的log文件,并且在一个独立的线程中创建新的checkpoint。
新的checkpoint包含了在切换到新log文件之前的状态变化。
当这个集群有数百万文件的时候,创建新的checkpoint会花上几分钟的时间。
当checkpoint建立完毕,会写到本地和远程的磁盘。
?
第8页对于master的恢复,只需要最新的checkpoint以及后续的log文件。
旧的checkpoint及其log文件可以删掉了,虽然我们还是保存几个checkpoint以及log,用来防止比较大的故障产生。
在checkpoint的时候得故障并不会导致正确性受到影响,因为恢复的代码会检查并且跳过不完整的checkpoint。
2.7一致性模型GFS是一个松散的一致性检查的模型,通过简单高效的实现,来支持我们的高度分布式计算的应用。
我们在这里讨论的GFS的可靠性以及对应用的可靠性。
我们也强调了GFS如何达到这些可靠性,实现细节在本论文的其他部分实现。
2.7.1GFS的可靠性保证文件名字空间的改变(比如,文件的创建)是原子操作。
他们是由master来专门处理的。
名字空间的锁定保证了操作的原子性以及正确性(4.1节);master的操作日志定义了这些操作的全局顺序(2.6.3)什么是文件区,文件区就是在文件中的一小块内容。
不管数据变化成功还是失败,是否是并发的数据变化,一个数据变化导致的一个文件区的状态依赖于这个变化的类型。
表一列出了这些结果。
当所有的客户端都看到的是相同的数据的时候,并且与这些客户端从哪个数据的副本读取无关的时候,一个文件区是一致性的。
一个文件区是确定的,当数据发生变化了,在一致性的基础上,客户端将会看到这个全部的变化。
当一个更改操作成功完成,没有并发写冲突,那么受影响的区就是确定的了(并且潜在一致性):
所有客户端都可以看到这个变化是什么。
并发成功操作使得文件区是不确定的,但是是一致性的:
所有客户端都看到了相同的数据,但是并不能却分到底什么变化发生了。
通常,他是由好多个变动混合片断组成。
一个失败的改变使得一个文件区不一致(因此也不确定):
不同的用户可能在不同时间看到不同的数据。
我们接下来会描述我们的应用如何能够辨别确定的和不确定的区块。
应用程序并不需要进一步区分不同种类的不确定区。
数据更改可能是写一个记录或者是一个记录增加(writes/recordappends)。
写操作会导致一个应用指定的文件位置的数据写入动作。
记录增加会导致数据(记录)增加,这个增加即使是在并发操作中也至少是一个原子操作,但是在并发recordappend中,GFS选择一个偏移量(3.3)增加。
(与之对应的是,一个”普通”?
第9页增加操作是类似一个客户端相信是写到当前文件最底部的一个操作)。
我们把偏移量返回给客户端,并且标志包含这个纪录的确定的区域的开始。
另外,GFS可以在这些记录之间增加填充,或者仅仅是记录的重复。
这些确定区间之间的填充或者记录的重复是不一致的,并且通常是因为用户记录数据比较小造成的。
在一系列成功的改动之后,改动后的文件区是确保确定的,并且包含了最后一个改动所写入的数据。
GFS通过(a)对所有的数据副本,按照相同顺序对chunk进行提交数据的改动来保证这样的一致性(3.1节),并且(b)采用chunk的版本号码控制,来检查是否有过期的chunk改动,这种通常发生在chunkserver宕机的情况下(4.5节)。
过期的副本将不参加到改动或者提交给master,让master通知客户端这个副本chunk的位置。
他们属于最早需要回收的垃圾chunk。
另外,由于客户端会cache这个chunk的位置,他们可能会在信息刷新之前读到这个过期的数据副本。
这个故障潜在发生的区间受到chunk位置cache的有效期限制,并且也受到下次重新打开文件的限制,重新打开文件会把这个文件所有的chunk相关的cache信息全部丢弃重新设置。
此外,由于多数文件都是只是追加数据,过期的数据副本通常返回一个较早的chunk尾部(也就是说这种模式下,过期的chunk返回的仅仅是说,这个chunk它以为是最后一个chunk,其实不是),而不是说返回一个过期的数据。
当一个热ader尝试和master联系,它会立刻得到最新的chunk位置。
在一个成功的数据更改之后,并且过了一段相对较长的时间,元器件的实效当然可以导致数据的损毁。
GFS通过master和chunkserver的普通握手来标记这些chunserver的损坏情况,并且使用checksum来检查数据是否损坏(5.2节)。
当发现问题的时候,数据会从一个有效的副本立刻重新恢复过来(4.
- 配套讲稿:
如PPT文件的首页显示word图标,表示该PPT已包含配套word讲稿。双击word图标可打开word文档。
- 特殊限制:
部分文档作品中含有的国旗、国徽等图片,仅作为作品整体效果示例展示,禁止商用。设计者仅对作品中独创性部分享有著作权。
- 关 键 词:
- The Google File System 中文 打印