GFS中文翻译

 

 

Google文件系统 
GFS是一个可扩展的分布式文件系统,用于大型的、分布式的、对大量数据进行访问的应用。它运行于廉价的普通硬件上,但能够提供容错功能。它能够给大量的用户提供整体性能较高的服务。 
1、设计概览 
1)设计想定 
GFS与过去的分布式文件系统有不少相同的目标,但GFS的设计受到了当前及预期的应用方面的工做量及技术环境的驱动,这反映了它与早期的文件系统明显不一样的设想。这就须要对传统的选择进行从新检验并进行彻底不一样的设计观点的探索。 
GFS与以往的文件系统的不一样的观点以下: 
1、部件错误再也不被看成异常,而是将其做为常见的状况加以处理。由于文件系统由成百上千个用于存储的机器构成,而这些机器是由廉价的普通部件组成并被大量的客户机访问。部件的数量和质量使得一些机器随时都有可能没法工做而且有一部分还可能没法恢复。因此实时地监控、错误检测、容错、自动恢复对系统来讲必不可少。 
2、按照传统的标准,文件都很是大。长度达几个GB的文件是很日常的。每一个文件一般包含不少应用对象。当常常要处理快速增加的、包含数以万计的对象、长度达TB的数据集时,咱们很难管理成千上万的KB规模的文件块,即便底层文件系统提供支持。所以,设计中操做的参数、块的大小必需要从新考虑。对大型的文件的管理必定要能作到高效,对小型的文件也必须支持,但没必要优化。 
3、大部分文件的更新是经过添加新数据完成的,而不是改变已存在的数据。在一个文件中随机的操做在实践中几乎不存在。一旦写完,文件就只可读,不少数据都有这些特性。一些数据可能组成一个大仓库以供数据分析程序扫描。有些是运行中的程序连续产生的数据流。有些是档案性质的数据,有些是在某个机器上产生、在另一个机器上处理的中间数据。因为这些对大型文件的访问方式,添加操做成为性能优化和原子性保证的焦点。而在客户机中缓存数据块则失去了吸引力。 
4、工做量主要由两种读操做构成:对大量数据的流方式的读操做和对少许数据的随机方式的读操做。在前一种读操做中,可能要读几百KB,一般达 1MB和更多。来自同一个客户的连续操做一般会读文件的一个连续的区域。随机的读操做一般在一个随机的偏移处读几个KB。性能敏感的应用程序一般将对少许数据的读操做进行分类并进行批处理以使得读操做稳定地向前推动,而不要让它来来回回的读。 
5、工做量还包含许多对大量数据进行的、连续的、向文件添加数据的写操做。所写的数据的规模和读类似。一旦写完,文件不多改动。在随机位置对少许数据的写操做也支持,但没必要很是高效。 
6、系统必须高效地实现定义无缺的大量客户同时向同一个文件的添加操做的语义。 
2)系统接口 
GFS提供了一个类似地文件系统界面,虽然它没有向POSIX那样实现标准的API。文件在目录中按层次组织起来并由路径名标识。 
3)体系结构: 
一个GFS集群由一个master和大量的chunkserver构成,并被许多客户(Client)访问。如图1所示。Masterchunkserver一般是运行用户层服务进程的Linux机器。只要资源和可靠性容许,chunkserverclient能够运行在同一个机器上。 
文件被分红固定大小的块。每一个块由一个不变的、全局惟一的64位的chunkhandle标识,chunkhandle是在块建立时由 master分配的。ChunkServer将块看成Linux文件存储在本地磁盘并能够读和写由chunkhandle和位区间指定的数据。出于可靠性考虑,每个块被复制到多个chunkserver上。默认状况下,保存3个副本,但这能够由用户指定。 
Master维护文件系统因此的元数据(metadata),包括名字空间、访问控制信息、从文件到块的映射以及块的当前位置。它也控制系统范围的活动,如块租约(lease)管理,孤儿块的垃圾收集,chunkserver间的块迁移。Master按期经过HeartBeat消息与每个 chunkserver通讯,给chunkserver传递指令并收集它的状态。 
与每一个应用相联的GFS客户代码实现了文件系统的API并与masterchunkserver通讯以表明应用程序读和写数据。客户与master的交换只限于对元数据(metadata)的操做,全部数据方面的通讯都直接和chunkserver联系。 
客户和chunkserver都不缓存文件数据。由于用户缓存的益处微乎其微,这是因为数据太多或工做集太大而没法缓存。不缓存数据简化了客户程序和整个系统,由于没必要考虑缓存的一致性问题。但用户缓存元数据(metadata)。Chunkserver也没必要缓存文件,由于块时做为本地文件存储的。 
4)单master 
只有一个master也极大的简化了设计并使得master能够根据全局状况做出先进的块放置和复制决定。可是咱们必需要将master对读和写的参与减至最少,这样它才不会成为系统的瓶颈。Client历来不会从master读和写文件数据。Client只是询问master它应该和哪一个 chunkserver联系。Client在一段限定的时间内将这些信息缓存,在后续的操做中Client直接和chunkserver交互。 
以图1解释一下一个简单的读操做的交互。 
1client使用固定的块大小将应用程序指定的文件名和字节偏移转换成文件的一个块索引(chunk index)。 
2、给master发送一个包含文件名和块索引的请求。 
3master回应对应的chunk handle和副本的位置(多个副本)。 
4client以文件名和块索引为键缓存这些信息。(handle和副本的位置)。 
5Client 向其中一个副本发送一个请求,极可能是最近的一个副本。请求指定了chunk handlechunkserverchunk handle标识chunk)和块内的一个字节区间。 
6、除非缓存的信息再也不有效(cache for a limited time)或文件被从新打开,不然之后对同一个块的读操做再也不须要clientmaster间的交互。 
一般Client能够在一个请求中询问多个chunk的地址,而master也能够很快回应这些请求。 
5)块规模: 
块规模是设计中的一个关键参数。咱们选择的是64MB,这比通常的文件系统的块规模要大的多。每一个块的副本做为一个普通的Linux文件存储,在须要的时候能够扩展。 
块规模较大的好处有: 
1、减小clientmaster之间的交互。由于读写同一个块只是要在开始时向master请求块位置信息。对于读写大型文件这种减小尤其重要。即便对于访问少许数据的随机读操做也能够很方便的为一个规模达几个TB的工做集缓缓存块位置信息。 
2Client在一个给定的块上极可能执行多个操做,和一个chunkserver保持较长时间的TCP链接能够减小网络负载。 
3、这减小了master上保存的元数据(metadata)的规模,从而使得能够将metadata放在内存中。这又会带来一些别的好处。 
不利的一面: 
一个小文件可能只包含一个块,若是不少Client访问改文件的话,存储这些块的chunkserver将成为访问的热点。但在实际应用中,应用程序一般顺序地读包含多个块的文件,因此这不是一个主要问题。 
6)元数据(metadata): 
master存储了三中类型的metadata:文件的名字空间和块的名字空间,从文件到块的映射,块的副本的位置。全部的metadata都放在内存中。前两种类型的metadata经过向操做日志登记修改而保持不变,操做日志存储在master的本地磁盘并在几个远程机器上留有副本。使用日志使得咱们能够很简单地、可靠地更新master的状态,即便在master崩溃的状况下也不会有不一致的问题。相反,mater在每次启动以及当有 chuankserver加入的时候询问每一个chunkserver的所拥有的块的状况。 
A、内存数据结构: 
由于metadata存储在内存中,因此master的操做很快。进一步,master能够轻易并且高效地按期在后台扫描它的整个状态。这种按期地扫描被用于实现块垃圾收集、chunkserver出现故障时的副本复制、为平衡负载和磁盘空间而进行的块迁移。 
这种方法的一个潜在的问题就是块的数量也即整个系统的容量是否受限与master的内存。实际上,这并非一个严重的问题。Master为每一个 64MB的块维护的metadata不足64个字节。除了最后一块,文件全部的块都是满的。相似的,每一个文件的名字空间数据也不足64个字节,由于文件名是以一种事先肯定的压缩方式存储的.若是要支持更大的文件系统,那么增长一些内存的方法对于咱们将元数据(metadata)保存在内存种所得到的简单性、可靠性、高性能和灵活性来讲,这只是一个很小的代价。 
B、块位置: 
master并不为chunkserver所拥有的块的副本的保存一个不变的记录。它在启动时经过简单的查询来得到这些信息。Master能够保持这些信息的更新,由于它控制全部块的放置并经过HeartBeat消息来监控chunkserver的状态。 
这样作的好处:由于chunkserver可能加入或离开集群、改变路径名、崩溃、重启等,一个集群重有成百个server,这些事件常常发生,这种方法就排除了masterchunkserver之间的同步问题。 
另外一个缘由是:只有chunkserver才能肯定它本身到底有哪些块,因为错误,chunkserver中的一些块可能会很天然的消失,这样在master中就没有必要为此保存一个不变的记录。 
C、操做日志: 
操做日志包含了对metadata所做的修改的历史记录。它做为逻辑时间线定义了并发操做的执行顺序。文件、块以及它们的版本号都由它们被建立时的逻辑时间而惟一地、永久地被标识。 
操做日志是如此的重要,咱们必需要将它可靠地保存起来,而且只有在metadata的改变固定下来以后才将变化呈现给用户。因此咱们将操做日志复制到数个远程的机器上,而且只有在将相应的日志记录写到本地和远程的磁盘上以后才回答用户的请求。 
Master能够用操做日志来恢复它的文件系统的状态。为了将启动时间减至最小,日志就必需要比较小。每当日志的长度增加到超过必定的规模后,master就要检查它的状态,它能够从本地磁盘装入最近的检查点来恢复状态。 
建立一个检查点比较费时,master的内部状态是以一种在建立一个检查点时并不耽误即将到来的修改操做的方式来组织的。Master切换到一个新的日子文件并在一个单独的线程中建立检查点。这个新的检查点记录了切换前全部的修改。在一个有数十万文件的集群中用一分钟左右就能完成。建立完后,将它写入本地和远程的磁盘。 
7)数据完整性 
名字空间的修改必须是原子性的,它们只能有master处理:名字空间锁保证了操做的原子性和正确性,而master的操做日志在全局范围内定义了这些操做的顺序。 
文件区间的状态在修改以后依赖于修改的类型,不论操做成功仍是失败,也不管是不是并发操做。若是不论从哪一个副本上读,全部的客户都看到一样的数据,那么文件的这个区域就是一致的。若是文件的区域是一致的而且用户能够看到修改操做所写的数据,那么它就是已定义的。若是修改是在没有并发写操做的影响下完成的,那么受影响的区域是已定义的,全部的client都能看到写的内容。成功的并发写操做是未定义但倒是一致的。失败的修改将使区间处于不一致的状态。 
Write操做在应用程序指定的偏移处写入数据,而record append操做使得数据(记录)即便在有并发修改操做的状况下也至少原子性的被加到GFS指定的偏移处,偏移地址被返回给用户。 
在一系列成功的修改操做后,最后的修改操做保证文件区域是已定义的。GFS经过对全部的副本执行一样顺序的修改操做而且使用块版本号检测过期的副本(因为chunkserver退出而致使丢失修改)来作到这一点。 
由于用户缓存了会位置信息,因此在更新缓存以前有可能从一个过期的副本中读取数据。但这有缓存的截止时间和文件的从新打开而受到限制。 
在修改操做成功后,部件故障仍能够是数据受到破坏。GFS经过masterchunkserver间按期的handshake,借助校验和来检测对数据的破坏。一旦检测到,就从一个有效的副本尽快从新存储。只有在GFS检测前,全部的副本都失效,这个块才会丢失。 
2、系统交互 
1)租约(lease)和修改顺序: 
2)数据流 
咱们的目标是充分利用每一个机器的网络带宽,避免网络瓶颈和延迟 
为了有效的利用网络,咱们将数据流和控制流分离。数据是以流水线的方式在选定的chunkerserver链上线性的传递的。每一个机器的整个对外带宽都被用做传递数据。为避免瓶颈,每一个机器在收到数据后,将它收到数据尽快传递给离它最近的机器。 
3)原子性的record Append 
GFS提供了一个原子性的添加操做:record append。在传统的写操做中,client指定被写数据的偏移位置,向同一个区间的并发的写操做是不连续的:区间有可能包含来自多个client的数据碎片。在record append中, client只是指定数据。GFS在其选定的偏移出将数据至少原子性的加入文件一次,并将偏移返回给client 
在分布式的应用中,不一样机器上的许多client可能会同时向一个文件执行添加操做,添加操做被频繁使用。若是用传统的write操做,可能须要额外的、复杂的、开销较大的同步,例如经过分布式锁管理。在咱们的工做量中,这些文件一般以多个生产者单个消费者队列的方式或包含从多个不一样 client的综合结果。 
Record append和前面讲的write操做的控制流差很少,只是在primary上多了一些逻辑判断。首先,client将数据发送到文件最后一块的全部副本上。而后向primary发送请求。Primary检查添加操做是否会致使该块超过最大的规模(64M)。若是这样,它将该块扩充到最大规模,并告诉其它副本作一样的事,同时通知client该操做须要在下一个块上从新尝试。若是记录知足最大规模的要求,primary就会将数据添加到它的副本上,并告诉其它的副本在在一样的偏移处写数据,最后primaryclient报告写操做成功。若是在任何一个副本上record append操做失败,client将从新尝试该操做。这时候,同一个块的副本可能包含不一样的数据,由于有的可能复制了所有的数据,有的可能只复制了部分。GFS不能保证全部的副本每一个字节都是同样的。它只保证每一个数据做为一个原子单元被写过至少一次。这个是这样得出的:操做要是成功,数据必须在全部的副本上的一样的偏移处被写过。进一步,从这之后,全部的副本至少和记录同样长,因此后续的记录将被指定到更高的偏移处或者一个不一样的块上,即便另外一个副本成了primary。根据一致性保证,成功的record append操做的区间是已定义的。而受到干扰的区间是不一致的。 
4)快照(snapshot 
快照操做几乎在瞬间构造一个文件和目录树的副本,同时将正在进行的其余修改操做对它的影响减至最小。 
咱们使用copy-on-write技术来实现snapshot。当master受到一个snapshot请求时,它首先将要snapshot的文件上块上的lease。这使得任何一个向这些块写数据的操做都必须和master交互以找到拥有lease的副本。这就给master一个建立这个块的副本的机会。 
副本被撤销或终止后,master在磁盘上登记执行的操做,而后复制源文件或目录树的metadata以对它的内存状态实施登记的操做。这个新建立的snapshot文件和源文件(其metadata)指向相同的块(chunk)。 
Snapshot以后,客户第一次向chunk c写的时候,它发一个请求给master以找到拥有lease的副本。Master注意到chunk c的引用记数比1大,它延迟对用户的响应,选择一个chunk handle C’,而后要求每一有chunk c的副本的chunkserver建立一个块C’。每一个chunkserver在本地建立chunk C’避免了网络开销。从这之后和对别的块的操做没有什么区别。 
3MASTER操做 
MASTER执行全部名字空间的操做,除此以外,他还在系统范围管理数据块的复制:决定数据块的放置方案,产生新数据块并将其备份,和其余系统范围的操做协同来确保数据备份的完整性,在全部的数据块服务器之间平衡负载并收回没有使用的存储空间。 
3.1 名字空间管理和加锁 
与传统文件系统不一样的是,GFS没有与每一个目录相关的能列出其全部文件的数据结构,它也不支持别名(unix中的硬链接或符号链接),无论是对文件或是目录。GFS的名字空间逻辑上是从文件元数据到路径名映射的一个查用表。 
MASTER在执行某个操做前都要得到一系列锁,例如,它要对/d1/d2…/dn/leaf执行操做,则它必须得到/d1/d1/d2/d1/d2/…/dn的读锁,/d1/d2…/dn/leaf的读锁或写锁(其中leaf可使文件也能够是目录)。MASTER操做的并行性和数据的一致性就是经过这些锁来实现的。 
3.2 备份存储放置策略 
一个GFS集群文件系统多是多层分布的。通常状况下是成千上万个文件块服务器分布于不一样的机架上,而这些文件块服务器又被分布于不一样机架上的客户来访问。所以,不一样机架上的两台机器之间的通讯可能经过一个或多个交换机。数据块冗余配置策略要达到连个目的:最大的数据可靠性和可用性,最大的网络带宽利用率。所以,若是仅仅把数据的拷贝置于不一样的机器上很难知足这两个要求,必须在不一样的机架上进行数据备份。这样即便整个机架被毁或是掉线,也能确保数据的正常使用。这也使数据传输,尤为是读数据,能够充分利用带宽,访问到多个机架,而写操做,则不得不涉及到更多的机架。 
3.3 产生、重复制、重平衡数据块 
MASTER产生新的数据块时,如何放置新数据块,要考虑以下几个因素:(1)尽可能放置在磁盘利用率低的数据块服务器上,这样,慢慢地各服务器的磁盘利用率就会达到平衡。(2)尽可能控制在一个服务器上的新建立的次数。(3)因为上一小节讨论的缘由,咱们须要把数据块放置于不一样的机架上。 
MASTER在可用的数据块备份低于用户设定的数目时须要进行重复制。这种状况源于多种缘由:服务器不可用,数据被破坏,磁盘被破坏,或者备份数目被修改。每一个被须要重复制的数据块的优先级根据如下几项肯定:第一是如今的数目距目标的距离,对于能阻塞用户程序的数据块,咱们也提升它的优先级。最后, MASTER按照产生数据块的原则复制数据块,并把它们放到不一样的机架内的服务器上。 
MASTER周期性的平衡各服务器上的负载:它检查chunk分布和负载平衡,经过这种方式来填充一个新的服务器而不是把其余的内容通通放置到它上面带来大量的写数据。数据块放置的原则与上面讨论的相同,此外,MASTER还决定那些数据块要被移除,原则上他会清除那些空闲空间低于平均值的那些服务器。 
3.4 垃圾收集 
在一个文件被删除以后,GFS并不当即收回磁盘空间,而是等到垃圾收集程序在文件和数据块级的的检查中收回。 
当一个文件被应用程序删除以后,MASTER会当即记录下这些变化,但文件所占用的资源却不会被当即收回,而是从新给文件命了一个隐藏的名字,并附上了删除的时间戳。在MASTER按期检查名字空间时,它删除超过三天(能够设定)的隐藏的文件。在此以前,能够以一个新的名字来读文件,还能够之前的名字恢复。当隐藏的文件在名字空间中被删除之后,它在内存中的元数据即被擦除,这就有效地切断了他和全部数据块的联系。 
在一个类似的按期的名字空间检查中,MASTER确认孤儿数据块(不属于任何文件)并擦除他的元数据,在和MASTER的心跳信息交换中,每一个服务器报告他所拥有的数据块,MASTER返回元数据不在内存的数据块,服务器便可以删除这些数据块。 
3.5 过期数据的探测 
在数据更新时若是服务器停机了,那么他所保存的数据备份就会过期。对每一个数据块,MASTER设置了一个版本号来区别更新过的数据块和过期的数据块。 
MASTER受权一个新的lease时,他会增长数据块的版本号并会通知更新数据备份。MASTER和备份都会记录下当前的版本号,若是一个备份当时不可用,那么他的版本号不可能提升,当ChunkServer从新启动并向MASTER报告他的数据块集时,MASTER就会发现过期的数据。 
MASTER在按期的垃圾收集程序中清除过期的备份,在此之前,处于效率考虑,在各客户及英大使,他会认为根本不存在过期的数据。做为另外一个安全措施, MASTER在给客户及关于数据块的应答或是另一个读取数据的服务器数据是都会带上版本信息,在操做前客户机和服务器会验证版本信息以确保获得的是最新的数据。 
4、容错和诊断 
4.1 高可靠性 
4.1.1 快速恢复 
无论如何终止服务,MASTER和数据块服务器都会在几秒钟内恢复状态和运行。实际上,咱们不对正常终止和不正常终止进行区分,服务器进程都会被切断而终止。客户机和其余的服务器会经历一个小小的中断,而后它们的特定请求超时,从新链接重启的服务器,从新请求。 
4.1.2 数据块备份 
如上文所讨论的,每一个数据块都会被备份到放到不一样机架上的不一样服务器上。对不一样的名字空间,用户能够设置不一样的备份级别。在数据块服务器掉线或是数据被破坏时,MASTER会按照须要来复制数据块。 
4.1.3 MASTER备份 
为确保可靠性,MASTER的状态、操做记录和检查点都在多台机器上进行了备份。一个操做只有在数据块服务器硬盘上刷新并被记录在MASTER和其备份的上以后才算是成功的。若是MASTER或是硬盘失败,系统监视器会发现并经过改变域名启动它的一个备份机,而客户机则仅仅是使用规范的名称来访问,并不会发现MASTER的改变。 
4.2 数据完整性 
每一个数据块服务器都利用校验和来检验存储数据的完整性。缘由:每一个服务器随时都有发生崩溃的可能性,而且在两个服务器间比较数据块也是不现实的,同时,在两台服务器间拷贝数据并不能保证数据的一致性。 
每一个Chunk64kB的大小分红块,每一个块有32位的校验和,校验和和日志存储在一块儿,和用户数据分开。 
在读数据时,服务器首先检查与被读内容相关部分的校验和,所以,服务器不会传播错误的数据。若是所检查的内容和校验和不符,服务器就会给数据请求者返回一个错误的信息,并把这个状况报告给MASTER。客户机就会读其余的服务器来获取数据,而MASTER则会从其余的拷贝来复制数据,等到一个新的拷贝完成时,MASTER就会通知报告错误的服务器删除出错的数据块。 
附加写数据时的校验和计算优化了,由于这是主要的写操做。咱们只是更新增长部分的校验和,即便末尾部分的校验和数据已被损坏而咱们没有检查出来,新的校验和与数据会不相符,这种冲突在下次使用时将会被检查出来。 
相反,若是是覆盖现有数据的写,在写之前,咱们必须检查第一和最后一个数据块,而后才能执行写操做,最后计算和记录校验和。若是咱们在覆盖之前不先检查首位数据块,计算出的校验和则会由于没被覆盖的数据而产生错误。 
在空闲时间,服务器会检查不活跃的数据块的校验和,这样能够检查出不常常读的数据的错误。一旦错误被检查出来,服务器会拷贝一个正确的数据块来代替错误的。 
4.3 诊断工具 
普遍而细致的诊断日志以微小的代价换取了在问题隔离、诊断、性能分析方面起到了重大的做用。GFS服务器用日志来记录显著的事件(例如服务器停机和启动)和远程的应答。远程日志记录机器之间的请求和应答,经过收集不一样机器上的日志记录,并对它们进行分析恢复,咱们能够完整地重现活动的场景,并用此来进行错误分析。 
6 测量 
6.1 测试环境 
一台主控机,两台主控机备份,16台数据块服务器,16台客户机。 
每台机器:2PIII1.4G处理器,2G内存,280G5400rpm的硬盘,1100Mbps全双工网卡 
19台服务器链接到一个HP2524交换机上,16台客户机俩接到领外一台交换机上,两台交换机经过1G的链路相连。缓存

相关文章
相关标签/搜索