第三章 磁盘大挪移——磁盘原理与技术 详解
第一十零节 固态存储介质和固态硬盘
3.10.4 Flash芯片的通病
Flash芯片在写入数据的时候有诸多效率低下的地方。包括现在常用的U盘以及SSD中的Flash芯片,或者Bios常用的EEPROM,它们都不可避免。
1. Flash芯片存储的通病之一:Erase Before Overwrite
对于机械磁盘来说,磁盘可以直接用磁头将对应的区域磁化成任何信号,如果之前保存的数据是1,新数据还是1,则磁头对1磁化,结果还是1;如果新数据是0,则磁头对1磁化,结果就变成了0。而Flash则不然,如果要向某个Block写入数据,则不管原来Block中是1还是0,新写入的数据是1还是0,必须先Erase整个Block为全1,然后才能向Block中写入新数据。这种额外的Erase操作大大增加了覆盖写的开销。
更难办的是,如果仅仅需要更改某个Block中的某个Page,那么此时就需要Erase整个Block,然后再写入这个Page。那么这个Block中除这个Page之外的其他Page中的数据在Erase之后岂不是都变成1了么?是的,所以,在Erase之前,需要将全部Block中的数据读入SSD的RAM Buffer,然后Erase整个Block,再将待写入的新Page中的数据在RAM中覆盖到Block中对应的Page,然后将整个更新后的Block写入Flash芯片中。可以看到,这种机制更加大了写开销,形成了大规模的写惩罚。这也是为何SSD的缓存通常很大的原因。
就像CDRW光盘一样,如果你只需要更改其上的几KB数据,那么就要先复制出全盘700MB的数据,然后擦除所有700MB,然后再写入更改了几KB数据的700MB数据。
SSD的这种写惩罚被称为Write Amplification(写扩大),我们依然使用写惩罚这个词。写惩罚有不同的惩罚倍数,比如,需要修改一个512KB的Block中的一个4KB的Page,此时的写惩罚倍数=512KB/4KB=128。小块随机写IO会产生大倍数的写惩罚。
当SSD当向Flash中的Free Space中写入数据时,并没有写惩罚,因为Free Space自从上次被整盘Erase后是没有发生任何写入动作的。这里又牵渗到一个比较有趣的问题,即存储介质如何知道哪里是Free Space,哪里是Occupied Space呢?本书中多个地方论述过这一点。只有文件系统知道存储介质中哪些数据是没用的,而哪些正在被文件系统所占用,这是绝对无可置疑的,除非文件系统通过某种途径通告存储介质。SSD也不例外,一块刚被全部Erase的SSD,其上所有Block对于文件系统或者SSD本身来讲,都可以认为是Free Space。随着数据不断的写入,SSD会将曾经被写入的块的位置记录下来,记录到一份Bitmap中,每一比特表示Flash中的一个Block。对于文件系统而言,删除文件的过程并不是向这个文件对应的存储介质空间内覆盖写入全0或者1的过程,而只是对元数据的更改,所以只会更改元数据对应的存储介质区域,因此,删除文件的过程并没有为存储介质自身制造Free Space。所以说,对于SSD本身来讲,Free Space只会越来越少,最后导致没有Free Space,导致每个写动作都产生写惩罚,类似Copy On Write,而且Copy和Write的很有可能都是一些在文件系统层已经被删除的数据,做了很多无用功,写性能急剧下降。对于一块使用非常久的SSD来讲,就算它在被挂载到文件系统之后,其上没有检测到任何文件,文件系统层剩余空间为100%,这种情况下,对于SSD本身来讲,Free Space的比例很有可能却是0,也就是说只要曾经用到过多少,那么那个水位线就永远被标记在那里。