利用分布式缓存在固态存储设备中处理原子命令的制作方法

文档序号:16626893发布日期:2019-01-16 06:11阅读:183来源:国知局
利用分布式缓存在固态存储设备中处理原子命令的制作方法
本申请涉及存储
技术领域
,尤其涉及存储设备中提供分布式缓存的方法与装置。
背景技术
:参看图1,展示了存储设备的框图。固态存储设备102同主机相耦合,用于为主机提供存储能力。主机同固态存储设备102之间可通过多种方式相耦合,耦合方式包括但不限于通过例如sata(serialadvancedtechnologyattachment,串行高级技术附件)、scsi(smallcomputersysteminterface,小型计算机系统接口)、sas(serialattachedscsi,串行连接scsi)、ide(integrateddriveelectronics,集成驱动器电子)、usb(universalserialbus,通用串行总线)、pcie(peripheralcomponentinterconnectexpress,pcie,高速外围组件互联)、nvme(nvmexpress,高速非易失存储)、以太网、光纤通道、无线通信网络等连接主机与固态存储设备102。主机可以是能够通过上述方式同存储设备相通信的信息处理设备,例如,个人计算机、平板电脑、服务器、便携式计算机、网络交换机、路由器、蜂窝电话、个人数字助理等。存储设备102包括接口103、控制部件104、一个或多个nvm(非易失存储器,non-volatilememory)芯片105以及dram(dynamicrandomaccessmemory,动态随机访问存储器)110。nand闪存、相变存储器、feram、mram等是常见的nvm。接口103可适配于通过例如sata、ide、usb、pcie、nvme、sas、以太网、光纤通道等方式与主机交换数据。控制部件104用于控制在接口103、nvm芯片105以及固件存储器110之间的数据传输,还用于存储管理、主机逻辑地址到闪存物理地址映射、擦除均衡、坏块管理等。可通过软件、硬件、固件或其组合的多种方式实现控制部件104。控制部件104可以是fpga(field-programmablegatearray,现场可编程门阵列)、asic(applicationspecificintegratedcircuit,应用专用集成电路)或者其组合的形式。控制部件104也可以包括处理器或者控制器,在处理器或控制器中执行软件来操纵控制部件104的硬件来处理主机io命令。控制部件104还耦合到dram110,并可访问dram110的数据。在dram可存储ftl表和/或缓存的主机io命令的数据。控制部件104包括闪存接口控制器(或称为闪存通道控制器)。闪存接口控制器耦合到nvm芯片105,并以遵循nvm芯片105的接口协议的方式向nvm芯片105发出命令,以操作nvm芯片105,并接收从nvm芯片105输出的命令执行结果。nvm芯片105的接口协议包括“toggle”、“onfi”等公知的接口协议或标准。存储器目标(target)是nand闪存封装内的共享芯片使能(ce,chipenable)信号的一个或多个逻辑单元(lun,logicunit)。每个逻辑单元具有逻辑单元号(logicunitnumber)。nand闪存封装内可包括一个或多个管芯(die)。典型地,逻辑单元对应于单一的管芯。逻辑单元可包括多个平面(plane)。逻辑单元内的多个平面可以并行存取,而nand闪存芯片内的多个逻辑单元可以彼此独立地执行命令和报告状态。在可从http://www.micron.com/~/media/documents/products/other%20documents/onfi3_0gold.ashx获得的“opennandflashinterfacespecification(revision3.0)”中,提供了关于目标(target)、逻辑单元、lun、平面(plane)的含义,其为现有技术的一部分。固态存储设备中包括多个nvm芯片。每个nvm芯片包括一个或多个管芯(die)或逻辑单元(lun,logicunit)。管芯或逻辑单元之间可以并行响应读写操作。在同一管芯或逻辑单元上的多个读、写或擦除操作顺序执行。存储介质上通常按页来存储和读取数据。而按块来擦除数据。块包含多个页。存储介质上的页(称为物理页)具有固定的尺寸,例如17664字节。物理页也可以具有其他的尺寸。物理页中可以包括多个数据帧(dataframe),数据帧具有指定的尺寸,例如4096或4416字节。在固态存储设备中,利用ftl(flashtranslationlayer,闪存转换层)来维护从逻辑地址到物理地址的映射信息。逻辑地址构成了操作系统等上层软件所感知到的固态存储设备的存储空间。物理地址是用于访问固态存储设备的物理存储单元的地址。在现有技术中还可利用中间地址形态实施地址映射。例如将逻辑地址映射为中间地址,进而将中间地址进一步映射为物理地址。存储了从逻辑地址到物理地址的映射信息的表结构被称为ftl表。ftl表是固态存储设备中的重要元数据。通常ftl表的数据项记录了固态存储设备中以数据页为单位的地址映射关系。ftl表是固态存储设备中的重要元数据。通常ftl表的数据项记录了固态存储设备中以数据页为单位的地址映射关系。固态存储设备的ftl表具有较大的尺寸,例如若干gb级。而在固态存储设备关闭时,需要完整地保存ftl表,在固态存储设备启动时,需要完成ftl完全加载。ftl表包括多个ftl表条目(或称表项)。在一个实施例中,每个ftl表条目中记录了一个逻辑页地址与一个物理页的对应关系。在另一个例子中,每个ftl表条目中记录了连续的多个逻辑页地址与连续的多个物理页的对应关系。在又一个实施例中,每个ftl表条目中记录了逻辑块地址与物理块地址的对应关系。在依然又一个实施例中,ftl表中记录逻辑块地址与物理块地址的映射关系,和/或逻辑页地址与物理页地址的映射关系。一些固态存储设备中还提供备用电源,当发生意外断电时,由备用电源向存储设备提供临时的电能,用于备份ftl表等元数据以及处理尚未完成的命令。备用电源包括超级电容、铝电容、钽聚合物电容、锂电池等。将要备份的数据写入固态存储设备提供的日志区。固态存储设备再次上电时,从日志区恢复所备份的元数据。在nvme规范(http://nvmexpress.org/wp-content/uploads/nvm_express_1_2_1_gold_20160603.pdf)中定义了原子操作(atomicoperation)。原子操作包括原子写命令。为执行原子写命令,固态存储设备确保在原子写命令中指示的数据,要么都写入到固态存储设备中,要么都未写入到固态存储设备中,而不会有其他自行结果。当同时存在向相同或部分相同的地址写入数据的两个或更多原子写命令时,这些原子写命令的执行结果是如同这些原子写命令串行执行的。例如,参看下表1,原子写命令a向逻辑地址(logicblockaddress,lba)lba0-3写入数据,原子写命令b向逻辑地址lba1-4写入数据(表1中用“a”指示由原子写命令a写入的数据,而由“b”指示由原子写命令b写入的数据)。下表的第2行与第3行示出了命令a与命令b的正确执行结果。参看表1,一种可能的结果(如下表第2行所示)是lba0-3是写命令a所写入的数据,而lba4是写命令b所写入的数据,换句话说,写命令b先生效,原子性地更新了lba1-4,接下来写命令a生效,又原子性地更新了lba0-3。另一种可能的结果(如下表第3行所示)是lba0是写命令a所写入的数据,而lba2-4是写命令b所写入的数据,换句话说,写命令a先生效,原子性地更新了lba0-3,接下来写命令b生效,又原子性地更新了lba1-4。除了上面提到的两种结果,其他任何结果都不符合nvme规范对原子写命令的要求。表1lba0lba1lba2lba3lba4lba5lba6有效结果aaaab有效结果abbbb无效结果aabbb固态存储设备具有极高的io处理能力,每秒中处理上百万条io命令。在利用缓存加速io处理速度时,为每条io处理缓存任务成为固态存储性能的性能瓶颈。为进一步提升固态存储设备的性能,需要突破缓存任务引入的性能瓶颈。技术实现要素:本申请的目的包括在存储器中提供分布式缓存的方法与装置,用于提升存储设备处理缓存任务的性能。根据本申请的第一方面,提供了根据本申请第一方面的第一写命令处理方法,包括:接收来自主机的写命令;将写命令分配给多个cpu之中的第一cpu;第一cpu为写命令分配缓存单元;第一cpu将写命令的数据写入所分配的缓存单元;响应于写命令要写入的数据被全部写入缓存单元,第一cpu向主机指示写命令处理完成。根据本申请的第二方面,提供了根据本申请第二方面的第一读命令处理方法,包括:接收来自主机的读命令;依据读命令的逻辑地址范围,将读命令分配给多个cpu中的第一cpu;若读命令命中缓存单元,第一cpu从缓存单元中获取读命令所访问的数据,并提供给主机;若读命令未命中缓存单元,第一cpu根据读命令的逻辑地址范围获取对应的物理地址,并根据物理地址从存储器中读出数据,并提供给主机。根据本申请的第三方面,提供了根据本申请第三方面的第一io命令处理方法,包括:依据写命令访问的地址范围,将写命令分配给多个cpu中的第一cpu;第一cpu依据所述地址范围从第二cpu获取一个或多个缓存单元的使用权;第一cpu将写命令要写入的数据写入从第二cpu获取的缓存单元;指示写命令处理完成;以及第一cpu向第二cpu归还从第二cpu获取的缓存单元的使用权。根据本申请的第四方面,提供了根据本申请第四方面的第一io命令处理方法,包括:响应于收到写命令,依据写命令访问的地址范围,将写命令分配给多个cpu中的第一cpu;依据写命令访问的地址将写命令分为一个或多个子写命令;为每个子写命令分配缓存单元;若所分配的第一缓存单元属于第二cpu,第一cpu从第二cpu获取第一缓存单元的使用权;将每个子写命令要写入的数据写入所分配的缓存单元;指示写命令处理完成;以及第一cpu将第一缓存单元的使用权归还第二cpu。根据本申请的第五方面,提供了根据本申请第五方面的第一io命令处理方法,包括:响应于收到读命令,依据读命令访问的逻辑地址范围,将读令分配给多个cpu中的第一cpu;依据读命令访问的逻辑地址将读命令分为一个或多个子读命令;为每个子读命令分配缓存单元;若所分配的第一缓存单元属于第二cpu,第一cpu从第二cpu获取第一缓存单元的使用权;对于每个子读命令,若命中了所分配的缓存单元,从缓存单元获取数据,若缓存单元未命中所分配的缓存单元,从子读命令的逻辑地址对应的物理地址获取数据;指示读命令处理完成;以及第一cpu将第一缓存单元的使用权归还第二cpu。根据本申请的第五方面的第一io命令处理方法,提供了根据本申请第五方面的第二io命令处理方法,还包括:若缓存单元未命中所分配的缓存单元,从子读命令的逻辑地址对应的物理地址获取数据,并将所获取的数据写入所分配的缓存单元。根据本申请的第六方面,提供了根据本申请第六方面的第一io命令处理方法,包括:响应于收到读命令,依据读命令访问的地址范围,将读令分配给多个cpu中的第一cpu;依据读命令访问的地址将读命令分为一个或多个子读命令;为每个子读命令分配缓存单元;若所分配的第一缓存单元属于第二cpu,第一cpu从第二cpu获取第一缓存单元的使用权;对于每个子读命令,若命中了所分配的缓存单元,从缓存单元获取数据,若缓存单元未命中所分配的缓存单元,从子读命令访问的地址获取数据;指示读命令处理完成;以及第一cpu将第一缓存单元的使用权归还第二cpu。根据本申请的第七方面,提供了根据本申请第七方面的第一掉电处理方法,缓存单元的元数据指示了缓存单元在存储器中的地址及缓存单元的状态,该方法包括:响应于接收到异常掉电的提示,终止尚未完成的io命令的处理;依据掉电发生时缓存单元的状态识别需要备份的缓存单元;将需要备份的缓存单元及其元数据写入nvm芯片。根据本申请的第八方面,提供了根据本申请第八方面的第一原子写命令执行方法,包括:接收原子写命令,依据原子写命令访问的地址范围,将原子写命令拆分为多个子命令;获取待处理的子命令,并为子命令分配缓存单元;请求为子命令对应的缓存单元加锁;响应于为子命令对应的缓存单元加锁成功,将子命令的数据写入所分配的缓存单元。根据本申请的第九方面,提供了根据本申请的第九方面的第一原子写命令的执行方法,包括:接收原子写命令;将原子写命令分配给多个cpu中的第一cpu;依据原子写命令访问的地址范围,将原子写命令拆分为多个子命令;获取待处理的子命令,并为子命令分配缓存单元;请求为所分配的缓存单元加锁;响应于为所分配的缓存单元加锁成功,子命令的数据写入所分配的缓存单元。根据本申请的第十方面,提供了根据本申请第十方面的第一写命令处理装置,包括:命令接收模块,用于接收来自主机的写命令;命令分配模块,用于将写命令分配给多个cpu之中的第一cpu;缓存单元分配模块,用于使第一cpu为写命令分配缓存单元;数据写入模块,用于使第一cpu将写命令的数据写入所分配的缓存单元;命令处理完成指示模块,用于响应于写命令要写入的数据被全部写入缓存单元,使第一cpu向主机指示写命令处理完成。根据本申请的第十一方面,提供了根据本申请第十一方面的第一读命令处理装置,包括:命令接收模块,用于接收来自主机的读命令;命令分配模块,用于依据读命令的逻辑地址范围,将读命令分配给多个cpu中的第一cpu;数据获取模块,用于使第一cpu从缓存单元中获取读命令所访问的数据,并提供给主机;数据获取模块,还用于若读命令未命中缓存单元,使第一cpu根据读命令的逻辑地址范围获取对应的物理地址,并根据物理地址从存储器中读出数据,并提供给主机。根据本申请的第十二方面,提供了根据本申请第十二方面的第一io命令处理装置,包括:命令分配模块,用于依据写命令访问的地址范围,将写命令分配给多个cpu中的第一cpu;缓存单元使用权获取模块,用于使第一cpu依据所述地址范围从第二cpu获取一个或多个缓存单元的使用权;数据写入模块,用于使第一cpu将写命令要写入的数据写入从第二cpu获取的缓存单元;命令处理指示模块,用于指示写命令处理完成;以及缓存单元使用权归还模块,用于使第一cpu向第二cpu归还从第二cpu获取的缓存单元的使用权。根据本申请的第十三方面,提供了根据本申请第十三方面的第一io命令处理装置,包括:命令分配模块,用于响应于收到写命令,依据写命令访问的地址范围,将写命令分配给多个cpu中的第一cpu;命令拆分模块,用于依据写命令访问的地址将写命令分为一个或多个子写命令;缓存单元分配模块,用于为每个子写命令分配缓存单元;缓存单元使用权获取模块,用于若所分配的第一缓存单元属于第二cpu,使第一cpu从第二cpu获取第一缓存单元的使用权;数据写入模块,用于将每个子写命令要写入的数据写入所分配的缓存单元;命令处理指示模块,用于指示写命令处理完成;以及缓存单元使用权归还模块,用于使第一cpu将第一缓存单元的使用权归还第二cpu。根据本申请的第十四方面,提供了根据本申请第十四方面的第一io命令处理装置,包括:命令分配模块,用于响应于收到读命令,依据读命令访问的逻辑地址范围,将读令分配给多个cpu中的第一cpu;命令拆分模块,用于依据读命令访问的逻辑地址将读命令分为一个或多个子读命令;缓存单元分配模块,用于为每个子读命令分配缓存单元;缓存单元使用权获取模块,用于若所分配的第一缓存单元属于第二cpu,使第一cpu从第二cpu获取第一缓存单元的使用权;数据获取模块,用于对于每个子读命令,若命中了所分配的缓存单元,从缓存单元获取数据,若缓存单元未命中所分配的缓存单元,从子读命令的逻辑地址对应的物理地址获取数据;命令处理指示模块,用于指示读命令处理完成;以及缓存单元使用权归还模块,用于使第一cpu将第一缓存单元的使用权归还第二cpu。根据本申请的第十五方面,提供了根据本申请第十五方面的第一io命令处理装置,包括:命令分配模块,用于响应于收到读命令,依据读命令访问的地址范围,将读令分配给多个cpu中的第一cpu;命令拆分模块,用于依据读命令访问的地址将读命令分为一个或多个子读命令;缓存单元分配模块,用于为每个子读命令分配缓存单元;缓存单元使用权获取模块,用于若所分配的第一缓存单元属于第二cpu,使第一cpu从第二cpu获取第一缓存单元的使用权;数据获取模块,用于对于每个子读命令,若命中了所分配的缓存单元,从缓存单元获取数据,若缓存单元未命中所分配的缓存单元,从子读命令访问的地址获取数据;命令处理指示模块,用于指示读命令处理完成;以及缓存单元使用权归还模块,用于使第一cpu将第一缓存单元的使用权归还第二cpu。根据本申请的第十六方面,提供了根据本申请第十六方面的第一掉电处理装置,缓存单元的元数据指示了缓存单元在存储器中的地址及缓存单元的状态,该装置包括:命令处理模块,用于响应于接收到异常掉电的提示,终止尚未完成的io命令的处理;待备份缓存单元识别模块,用于依据掉电发生时缓存单元的状态识别需要备份的缓存单元;数据写入模块,用于将需要备份的缓存单元及其元数据写入nvm芯片。根据本申请的第十七方面,提供了根据本申请第十七方面的第一原子写命令的执行装置,包括:命令接收模块,用于接收原子写命令,依据原子写命令访问的地址范围;命令拆分模块,用于将原子写命令拆分为多个子命令;命令获取模块,用于获取待处理的子命令;缓存单元分配模块,用于为子命令分配缓存单元;加锁模块,用于请求为子命令对应的缓存单元加锁;命令处理模块,用于响应于为子命令对应的缓存单元加锁成功,将子命令的数据写入所分配的缓存单元。根据本申请的第十八方面,提供了根据本申请第十八方面的第一原子写命令的执行装置,包括:命令接收装置,用于接收原子写命令;命令分配模块,用于将原子写命令分配给多个cpu中的第一cpu;命令拆分模块,用于依据原子写命令访问的地址范围,将原子写命令拆分为多个子命令;命令获取模块,用于获取待处理的子命令;缓存单元分配模块,用于为子命令分配缓存单元;加锁模块,用于为所分配的缓存单元加锁;数据写入模块,用于响应于为所分配的缓存单元加锁成功,子命令的数据写入所分配的缓存单元。根据本申请的第十九方面,提供了根据本申请第十九方面的第一固态存储设备,包括控制部件与nvm芯片,所述控制部件包括主机接口和用于访问存储器的介质接口,主机接口用于同主机交换命令与数据,控制部件还包括分配器和多个cpu,分配器耦合到主机接口,用于接收主机发送给存储设备的io命令,并将io命令分配给多个cpu之一;控制部件还耦合到外部存储器,外部存储器提供缓存单元;控制部件还耦合到nvm芯片,其中cpu用于执行根据本申请第一方面、第二方面、第三方面、第四方面、第五方面或者第六方面的方法。根据本申请的第二十方面,提供了根据本申请第二十方面的第一固态存储设备,包括多个cpu和外部存储器,外部存储器提供缓存单元,每个cpu管理多个缓存单元,缓存单元的元数据中记录了该缓存单元在存储器中的地址及缓存单元的状态,cpu响应于接收到异常掉电的提示,终止尚未完成的io命令的处理;依据掉电发生时缓存单元的状态识别需要备份的缓存单元;以及将需要备份的缓存单元及其元数据写入nvm芯片,其中cpu用于执行根据本申请第七方面的方法。根据本申请的第二十一方面,提供了根据本申请第二十一方面的第一固态存储设备,包括控制部件与nvm芯片,控制部件包括分配器和多个cpu,分配器耦合到主机接口,用于接收io命令,并将io命令分配给多个cpu之一;控制部件还耦合到外部存储器,外部存储器提供缓存单元;控制部件还耦合到nvm芯片,其中cpu用于执行根据本申请第八方面或第九方面的方法。根据本申请的第二十二方面,提供一种包括程序代码的程序,其中控制部件用于执行根据本申请第一方面的写命令处理方法。根据本申请的第二十三方面,提供一种包括程序代码的程序,其中控制部件用于执行根据本申请第二方面的读命令处理方法。根据本申请的第二十四方面,提供一种包括程序代码的程序,其中控制部件用于执行根据本申请第三方面的io命令处理方法。根据本申请的第二十五方面,提供了一种包括程序代码的程序,其中控制部件用于执行根据本申请第四方面的io命令处理方法。根据本申请的第二十六方面,提供了一种包括程序代码的程序,其中控制部件用于执行根据本申请第五方面的io命令处理方法。根据本申请的第二十七方面,提供了一种包括程序代码的程序,其中控制部件用于执行根据本申请第六方面的io命令处理方法。根据本申请的第二十八方面,提供了一种包括程序代码的程序,其中控制部件用于执行根据本申请第七方面的掉电处理方法。根据本申请的第二十九方面,提供了一种包括程序代码的程序,其中控制部件用于执行根据本申请第八方面的原子写命令执行方法。根据本申请的第三十方面,提供了一种包括程序代码的程序,其中控制部件用于执行根据本申请第九方面的原子写命令执行方法。根据本申请的第三十一方面,提供了根据本申请的第三十一方面的第一原子读命令的处理方法,包括:接收原子读命令;将原子读命令分配给多个cpu中的第一cpu;依据原子读命令访问的地址范围,将原子读命令拆分为多个子命令;获取待处理的子命令,并为子命令分配缓存单元;请求为所分配的缓存单元加锁;响应于加锁成功,若子命令命中缓存单元,将缓存单元中同子命令对应的数据提供给主机。根据本申请的第三十一方面的第一原子读命令的处理方法,提供了根据本申请的第三十一方面的第二原子读命令的处理方法,其中,若子命令未命中缓存单元,依据子命令的逻辑地址范围获取对应的物理地址,根据物理地址从nvm芯片中读出数据,并提供给主机。根据本申请的第三十一方面的第一或第二原子读命令的处理方法,提供了根据本申请的第三十一方面的第三原子读命令的处理方法,其中,还包括:依据原子读命令访问的地址范围,将原子读命令分配给多个cpu中的第一cpu。根据本申请的第三十一方面的第三原子读命令的处理方法,提供了根据本申请的第三十一方面的第四原子读命令的处理方法,其中,若原子读命令访问的地址范围完全属于第一cpu所管理的地址范围,将原子读命令分配给第一cpu。根据本申请的第三十一方面的第三原子读命令的处理方法,提供了根据本申请的第三十一方面的第五原子读命令的处理方法,其中,若原子读命令访问的地址范围的第一部分属于第一cpu所管理的地址范围,而原子读命令访问的地址范围的第二部分属于第二cpu所管理的地址范围,将原子读命令分配给第一cpu或第二cpu。根据本申请的第三十一方面的第一至第五之一的原子读命令的处理方法,提供了根据本申请的第三十一方面的第六原子读命令的处理方法,其中,还包括:若为子命令分配缓存单元失败,暂停对该子命令的处理。根据本申请的第三十一方面的第一至第六之一的原子读命令的处理方法,提供了根据本申请的第三十一方面的第七原子读命令的处理方法,其中,还包括:获取属于同一原子读命令的未被处理的多个子命令中按地址排序在最前的子命令;以及对该子命令进行处理。根据本申请的第三十一方面的第一至第六之一的原子读命令的处理方法,提供了根据本申请的第三十一方面的第八原子读命令的处理方法,其中,还包括:对于获取的子命令,仅当获取的子命令是所属的原子写命令的多个尚未处理的子命令中,按地址排序最前的子命令时,才为子命令分配缓存单元。根据本申请的第三十一方面的第一至第六之一的原子读命令的处理方法,提供了根据本申请的第三十一方面的第九原子读命令的处理方法,其中,还包括:对于获取的子命令,仅当获取的子命令是所属的原子读命令的多个尚未处理的子命令中,按地址排序最前的子命令时,才请求为子命令对应的缓存单元加锁。根据本申请的第三十一方面的第一至第六之一的原子读命令的处理方法,提供了根据本申请的第三十一方面的第十原子读命令的处理方法,其中,还包括:获取原子读命令的多个尚未处理的子命令中,按地址排序最前的子命令;以及请求为该子命令对应的缓存单元加锁。根据本申请的第三十一方面的第七至第十之一的原子读命令的处理方法,提供了根据本申请的第三十一方面的第十一原子读命令的处理方法,其中,还包括:对原子读命令的多个子命令按地址排序,是按照地址数值的升序排序,或者地址数值的降序排序。根据本申请的第三十一方面的第一至第十一之一的原子读命令的处理方法,提供了根据本申请的第三十一方面的第十二原子读命令的处理方法,其中,还包括:若要处理的子命令访问的地址范围属于第一cpu所管理的地址范围,第一cpu为子命令分配缓存单元,并请求为所分配的缓存单元加锁。根据本申请的第三十一方面的第一至第十二之一的原子读命令的处理方法,提供了根据本申请的第三十一方面的第十三原子读命令的处理方法,其中,还包括:若要处理的子命令访问的地址范围不属于第一cpu所管理的地址范围,第一cpu依据要处理的子命令访问的地址范围从其所属的第二cpu借用缓存单元。根据本申请的第三十一方面的第一至第十三之一的原子读命令的处理方法,提供了根据本申请的第三十一方面的第十四原子读命令的处理方法,其中,还包括:若要处理的子命令访问的地址范围不属于第一cpu所管理的地址范围,第一cpu依据要处理的子命令访问的地址范围从第二cpu获取所需的元数据,元数据中记录了缓存单元索引;以及第一cpu依据所获取的元数据为要处理的子命令分配缓存单元,并请求为所分配的缓存单元加锁。根据本申请的第三十一方面的第一至十三之一原子读命令的处理方法,提供了根据本申请的第三十一方面的第十五原子读命令的处理方法,其中,还包括:若要处理的子命令访问的地址范围不属于第一cpu所管理的地址范围,第一cpu依据要处理的子命令访问的地址范围从其所属的第二cpu获取缓存单元;以及第一cpu为要处理的子命令分配所获取的缓存单元,并请求为所分配的缓存单元加锁。根据本申请的第三十一方面的第一至第十五之一的原子读命令的处理方法,提供了根据本申请的第三十一方面的第十六原子读命令的处理方法,其中,还包括:若子命令未命中缓存单元,将从nvm芯片中获取的数据存储在缓存单元中。根据本申请的第三十一方面的第一至第十六之一的原子读命令的处理方法,提供了根据本申请的第三十一方面的第十七原子读命令的处理方法,其中,还包括:若已为该原子读命令对应的缓存单元全部加锁,响应于将所有子命令所对应的数据都提供给主机,向主机指示该原子读命令处理完成。根据本申请的第三十一方面的第十七原子读命令的处理方法,提供了根据本申请的第三十一方面的第十八原子读命令的处理方法,其中,还包括:若未为该原子读命令对应的缓存单元全部加锁,获取该原子读命令的多个子命令中的下一子命令。根据本申请的第三十一方面的第十七或第十八原子读命令的处理方法,提供了根据本申请的第三十一方面的第十九原子读命令的处理方法,其中,还包括:在该原子读命令的所有子命令对应的数据都提供给主机后,释放分配给该原子读命令的所有缓存单元的锁。根据本申请的第三十一方面的第十九原子读命令的处理方法,提供了根据本申请的第三十一方面的第二十原子读命令的处理方法,其中,还包括:对于借用的缓存单元,在该缓存单元的锁被释放后,归还所借用的缓存单元。根据本申请的第三十一方面的第二十原子读命令的处理方法,提供了根据本申请的第三十一方面的第二十一原子读命令的处理方法,其中,归还所借用的缓存单元包括:第一cpu向第二cpu指示所借用的缓存单元的元数据;响应于接收到第一cpu所指示的所借用的缓存单元的元数据,第二cpu恢复对缓存单元的管理。根据本申请的第三十二方面,提供了根据本申请的第三十二方面的第一原子命令的执行方法,包括:接收原子命令;若原子命令的类型为原子读命令,且需要满足一般原子性,将原子读命令分配给多个cpu中的第一cpu;依据原子读命令访问的地址范围,将原子读命令拆分为多个子命令;获取待处理的子命令,并为子命令分配缓存单元;请求为所分配的缓存单元加锁;响应于加锁成功,若子命令命中缓存单元,将缓存单元中同子命令对应的数据提供给主机。根据本申请的第三十二方面的第一原子命令的执行方法,提供了根据本申请的第三十二方面的第二原子命令的执行方法,其中,若子命令未命中缓存单元,依据子命令访问的地址范围获取对应的物理地址,根据物理地址从nvm芯片中读出数据,并提供给主机。根据本申请的第三十二方面的第一或第二原子命令的执行方法,提供了根据本申请的第三十二方面的第三原子命令的执行方法,其中,对于获取的子命令,若该子命令在其所属的原子读命令中的未被处理的多个子命令中的排序不为最前,则暂停对该子命令的处理。根据本申请的第三十二方面的第一至第三之一的原子命令的执行方法,提供了根据本申请的第三十二方面的第四原子命令的执行方法,其中,还包括:若已为该原子读命令对应的缓存单元全部加锁,响应于将所有子命令所对应的数据都提供给主机,向主机指示该原子读命令处理完成。根据本申请的第三十二方面的第四原子命令的执行方法,提供了根据本申请的第三十二方面的第五原子命令的执行方法,其中,还包括:若未为该原子读命令对应的缓存单元全部加锁,获取该原子读命令的多个子命令中的下一子命令。根据本申请的第三十二方面的第一至第五之一的原子命令的执行方法,提供了根据本申请的第三十二方面的第六原子命令的执行方法,其中,还包括:在该原子读命令的所有子命令对应的数据都提供给主机后,释放分配给该原子读命令的所有缓存单元的锁。根据本申请的第三十二方面的第一至第六之一的原子命令的执行方法,提供了根据本申请的第三十二方面的第七原子命令的执行方法,其中,还包括:若不需要满足一般原子性,不依赖为其他子命令的加锁结果和/或处理结果而处理每个子命令。根据本申请的第三十二方面的第一至第七之一的原子命令的执行方法,提供了根据本申请的第三十二方面的第八原子命令的执行方法,其中,还包括:若原子命令的类型为原子写命令,且需要满足一般原子性或掉电原子性,依据原子写命令访问的地址范围,将原子写命令拆分为多个子命令;获取待处理的子命令,并为子命令分配缓存单元;请求为子命令对应的缓存单元加锁;响应于为子命令对应的缓存单元加锁成功,将子命令的数据写入所分配的缓存单元。根据本申请的第三十二方面的第一至第七之一的原子命令的执行方法,提供了根据本申请的第三十二方面的第九原子命令的执行方法,其中,还包括:若原子命令的类型为原子写命令,且该原子写命令需要满足一般原子性或掉电原子性,将原子写命令分配给多个cpu中的第一cpu;依据原子写命令访问的地址范围,将原子写命令拆分为多个子命令;获取待处理的子命令,并为子命令分配缓存单元;请求为所分配的缓存单元加锁;响应于为所分配的缓存单元加锁成功,将子命令的数据写入所分配的缓存单元。根据本申请的第三十二方面的第八或第九原子命令的执行方法,提供了根据本申请的第三十二方面的第十原子命令的执行方法,其中,对于获取的子命令,若该子命令在其所属的原子写命令的未被处理的多个子命令中的排序不为最前,则暂停对该子命令的处理。根据本申请的第三十二方面的第八至第十原子命令的执行方法,提供了根据本申请的第三十二方面的第十一原子命令的执行方法,其中,还包括:若已为该原子写命令对应的缓存单元全部加锁,响应于将所有子命令所对应的数据都写入缓存单元,向主机指示该原子写命令处理完成。根据本申请的第三十二方面的第十一原子命令的执行方法,提供了根据本申请的第三十二方面的第十二原子命令的执行方法,其中,还包括:若未为该原子写命令对应的缓存单元全部加锁,获取该原子写命令的多个子命令中的下一子命令。根据本申请的第三十二方面的第八至第十二之一的原子命令的执行方法,提供了根据本申请的第三十二方面的第十三原子命令的执行方法,其中,还包括:在该原子写命令的所有子命令对应的数据都写入缓存单元后,释放分配给该原子写命令的所有缓存单元的锁。根据本申请的第三十二方面的第一原子命令的执行方法,提供了根据本申请的第三十二方面的第十三原子命令的执行方法,其中,还包括:若该原子写命令不需要满足一般原子性或掉电原子性,不依赖为其他子命令的加锁结果和/或处理结果而处理每个子命令。根据本申请的第三十三方面,提供了根据本申请的第三十三方面的第一原子读命令执行装置,包括:命令接收装置,用于接收原子读命令;命令分配模块,用于将原子读命令分配给多个cpu中的第一cpu;命令拆分模块,用于依据原子读命令访问的地址范围,将原子读命令拆分为多个子命令;缓存单元分配模块,用于获取待处理的子命令,并为子命令分配缓存单元;加锁模块,用于请求为所分配的缓存单元加锁;响应于加锁成功,若子命令命中缓存单元,将缓存单元中同子命令对应的数据提供给主机。根据本申请的第三十四方面,提供了根据本申请的第三十四方面的第一原子命令执行装置,包括:命令接收模块,用于接收原子命令;命令分配模块,用于若原子命令的类型为原子读命令,且该原子读命令需要满足一般原子性,将原子读命令分配给多个cpu中的第一cpu;命令拆分模块,用于依据原子读命令访问的地址范围,将原子读命令拆分为多个子命令;缓存单元分配模块,用于获取待处理的子命令,并为子命令分配缓存单元;加锁模块,用于请求为所分配的缓存单元加锁;数据读取模块,用于响应于加锁成功,若子命令命中缓存单元,将缓存单元中同子命令对应的数据提供给主机。根据本申请的第三十四方面的第一原子命令执行装置,提供了根据本申请的第三十四方面的第二原子命令执行装置,其中,还包括命令处理模块,用于若该原子读命令不需要满足一般原子性,不依赖为其他子命令的加锁结果和/或处理结果而处理每个子命令。根据本申请的第三十四方面的第一原子命令执行装置,提供了根据本申请的第三十四方面的第三原子命令执行装置,其中,还包括判断模块,用于判断原子命令的类型为原子写命令,且该原子写命令需要满足一般原子性或掉电原子性;命令拆分模块,还用于依据原子写命令访问的地址范围,将原子写命令拆分为多个子命令;缓存单元分配模块,还用于获取待处理的子命令,并为子命令分配缓存单元;加锁模块,还用于请求为子命令对应的缓存单元加锁;数据写入模块,用于响应于为子命令对应的缓存单元加锁成功,将子命令的数据写入所分配的缓存单元。根据本申请的第三十四方面的第一原子命令执行装置,提供了根据本申请的第三十四方面的第四原子命令执行装置,其中,还包括判断模块,用于判断原子命令的类型为原子写命令,且该原子写命令需要满足一般原子性或掉电原子性,命令分配模块,还用于将原子写命令分配给多个cpu中的第一cpu;命令拆分模块,还用于依据原子写命令访问的地址范围,将原子写命令拆分为多个子命令;缓存单元分配模块,还用于获取待处理的子命令,并为子命令分配缓存单元;加锁模块,还用于请求为所分配的缓存单元加锁;数据写入模块,还用于响应于为所分配的缓存单元加锁成功,将子命令的数据写入所分配的缓存单元。根据本申请的第三十四方面的第一原子命令执行装置,提供了根据本申请的第三十四方面的第五原子命令执行装置,其中,还包括判断模块,用于判断该原子写命令不需要满足一般原子性或掉电原子性;命令处理模块,还用于处理每个子命令,而无须依赖为其他子命令的加锁结果和/或处理结果。根据本申请的第三十五方面,提供了根据本申请的第三十五方面的第一固态存储设备,包括控制部件与nvm芯片,控制部件包括分配器和多个cpu,分配器耦合到主机接口,用于接收io命令,并将io命令分配给多个cpu之一;控制部件还耦合到外部存储器,外部存储器提供缓存单元;控制部件还耦合到nvm芯片。根据本申请的第三十五方面的第一固态存储设备,提供了根据本申请的第三十五方面的第二固态存储设备,其中包括:分配器,用于接收原子读命令,将原子读命令分配给多个cpu中的第一cpu;第一cpu,用于依据原子读命令访问的地址范围,将原子读命令拆分为多个子命令;获取待处理的子命令,并为子命令分配缓存单元;请求为所分配的缓存单元加锁;响应于加锁成功,若子命令命中缓存单元,将缓存单元中同子命令对应的数据提供给主机。根据本申请的第三十五方面的第一或第二固态存储设备,提供了根据本申请的第三十五方面的第三固态存储设备,其中:第一cpu,还用于确定原子命令的类型,若原子命令的类型为原子读命令,且该原子读命令需要满足一般原子性,依据原子读命令访问的地址范围,将原子读命令拆分为多个子命令;获取待处理的子命令,并为子命令分配缓存单元;请求为所分配的缓存单元加锁;响应于加锁成功,若子命令命中缓存单元,将缓存单元中同子命令对应的数据提供给主机。根据本申请的第三十五方面的第一至第三之一的固态存储设备,提供了根据本申请的第三十五方面的第四固态存储设备,其中,cpu用于执行上述的原子读命令执行方法,或者上述的原子命令执行方法。根据本申请的第三十六方面,提供了根据本申请的第三十六方面的第一包括程序的存储介质,当被载入固态存储设备并在固态存储设备上执行时,程序使固态存储设备执行上述的原子读命令的执行方法,或者上述的原子命令的执行方法。附图说明为了更清楚地说明本申请实施例或现有技术中的技术方案,下面将对实施例描述中所需要使用的附图作简单地介绍,显而易见地,下面描述中的附图仅仅是本申请的一些实施例,对于本领域普通技术人员来讲,在不付出创造性劳动的前提下,还可以根据这些附图获得其他的附图。图1为现有技术中的存储设备的框图;图2为根据本申请实施例的控制部件的框图;图3为根据本申请实施例的io命令分配的示意图;图4为根据本申请实施例的缓存单元的元数据的示意图;图5为根据本申请实施例的缓存单元的状态图;图6为根据本申请实施例的缓存单元借用的示意图;图7为根据本申请实施例的处理写命令的流程图;图8为根据本申请又一实施例的处理写命令的流程图;图9是根据本申请实施例的处理读命令的流程图;图10是根据本申请实施例的掉电处理的流程图;图11是根据本申请实施例的处理原子写命令的流程图;图12是根据本申请又一实施例的处理原子写命令的流程图;图13是根据本申请实施例的原子命令的示意图;图14为根据本申请实施例的缓存单元的示意图;图15为根据本申请实施例的缓存单元的示意图;图16是根据本申请又一实施例的原子命令的示意图;图17为根据本申请又一实施例的缓存单元的示意图;图18为根据本申请又一实施例的缓存单元的示意图;图19为根据本申请又一实施例的缓存单元的示意图。图20是根据本申请实施例的处理原子读命令的流程图;图21是根据本申请实施例的处理原子命令的流程图;图22是根据本申请又一实施例的原子命令的示意图;图23为根据本申请实施例的缓存单元的示意图;图24为根据本申请实施例的缓存单元的示意图;图25为根据本申请实施例的缓存单元的示意图;图26是根据本申请又一实施例的原子命令的示意图;图27为根据本申请实施例的缓存单元的示意图;图28为根据本申请实施例的缓存单元的示意图;图29为根据本申请实施例的缓存单元的示意图;图30是根据本申请又一实施例的原子命令的示意图;图31为根据本申请又一实施例的缓存单元的示意图;图32为根据本申请又一实施例的缓存单元的示意图;图33为根据本申请又一实施例的缓存单元的示意图;以及图34为根据本申请又一实施例的缓存单元的示意图。具体实施方式下面将结合本申请实施例中的附图,对本申请实施例中的技术方案进行清楚、完整地描述,显然,所描述的实施例是本申请一部分实施例,而不是全部的实施例。基于本申请中的实施例,本领域普通技术人员在没有做出创造性劳动前提下所获得的所有其他实施例,都属于本申请保护的范围。实施例一图2为根据本申请实施例的控制部件的框图。图2中示出的控制部件104包括主机接口210、分配器230、用于处理缓存任务的多个cpu(cpu0、cpu1、cpu2与cpu3)和用于访问nvm芯片105的介质接口220。主机接口210用于同主机交换命令与数据。在一个例子中,主机与存储设备通过nvme/pcie协议通信,主机接口210处理pcie协议数据包,提取出nvme协议命令,并向主机返回nvme协议命令的处理结果。分配器230耦合到主机接口210,用于接收主机发送给存储设备的io命令,并将io命令分配给用于处理缓存任务的多个cpu之一。分配器230可由cpu或专用硬件实现。控制部件104还耦合到外部存储器(例如,dram)110。参看图2,外部存储器110的部分空间(缓存单元0、缓存单元1、缓存单元2与缓存单元3)被用作缓存。用于处理缓存任务的多个cpu管理前端缓存的分配和使用。对于写命令,在cpu的指示下,将要写入的数据通过主机接口210从主机传输到dram110中的缓存单元,以及还将缓存单元中的数据通过介质接口220传输到nvm芯片105。可选地,写命令的数据也可直接传输到nvm芯片105,而不经过缓存单元。对于读命令,cpu识别缓存单元是否命中,若缓存单元命中,在cpu的指示下,从缓存单元获取数据发送给主机。若缓存单元未命中,从nvm芯片105获取数据发送给主机,以及可选地,用从nvm芯片105获取的数据替换缓存单元中的数据。用于处理缓存任务的多个cpu之间可彼此通信以交换信息。例如,cpu0向cpu1请求cpu1管理缓存单元的元数据,使得cpu0可操作由cpu1管理的缓存单元。cpu1向cpu2请求cpu2管理缓存单元的元数据,使得cpu1可操作由cpu2管理的缓存单元。控制部件104还包括ftl模块(未示出),用于将闪存访问命令的逻辑地址转换为物理地址,并对闪存实施管理,提供磨损均衡、垃圾回收等服务。,实施例二图3展示了根据本申请实施例的io命令分配的示意图。固态存储设备向主机展示了可访问的逻辑地址。在图3中,沿逻辑地址递增的方向,逻辑地址空间被分为多个区域(302、304……324),每个区域被分配给多个cpu(cpu0、cpu1、cpu2与cpu3)之一管理。可选地,将各区域轮流分配给cpu之一。例如,将区域302分配给cpu0,将区域304分配给cpu1将区域306分配给cpu2,将区域308分配给cpu3。接下来发生回绕,将区域310分配给cpu0,使得来自主机的io命令被尽量均匀地分配给多个cpu。每个区域的大小可配置。例如,每个区域为1mb。作为举例,主机提供的io命令访问的逻辑地址的范围不超过128kb,若将区域设置为大于128kb(例如,1mb),则使io命令访问的lba(逻辑地址)范围最多覆盖两个区域,进而仅需两个cpu同步元数据,也使更多的io命令访问的逻辑地址范围仅在一个区域内,并由单一cpu处理。作为又一个例子,每个区域的lba范围是4kb、8kb或16kb,以同主机发出的io命令访问的逻辑地址范围相近。作为另一个例子,将lba地址的低位的不同值映射到不同的cpu。可以理解地,逻辑地址空间有其他划分方式。例如,将逻辑地址空间分为同cpu数量相同的区域,每个区域由一个cpu管理。或者不论io命令的lba范围,而将io命令轮流分配给cpu。可选地,固态存储设备向主机展示了可访问的物理地址。io命令指示物理地址。以及将物理地址分为多个区域,每个区域被分配个多个cpu之一管理。以将逻辑地址区域分配给cpu的相同或相似策略,将物理地址区域分配给cpu。对于访问指示固态存储设备的物理地址的io命令,可使用物理地址直接访问nvm芯片,而无须使用ftl表。可选地,对io命令的物理地址进行映射,以获得映射后的地址,并用来访问nvm芯片。dram110提供缓存单元,每个缓存单元的大小是例如4kb。cpu管理缓存单元的分配与使用。同一时刻,一个缓存单元仅由cpu之一使用。实施例三图4展示了根据本申请实施例的缓存单元的元数据的示意图。每个cpu维护各自的缓存元数据。例如,参看图4,cpu0维护元数据0,cpu1维护元数据1……。元数据尺寸较小,可存储在cpu内部的存储器中,从而cpu可以低延迟地访问元数据。元数据指示了dram110中的缓存单元。例如,参看图4,元数据0是用于缓存单元402、404、406与408的元数据;元数据1是用于缓存单元412、414、416与418的元数据。通过维护元数据,cpu管理和使用缓存单元。以及通过向其他cpu“借用”元数据的部分,cpu之一管理和使用属于其他cpu的缓存单元。其中,每个缓存单元可包括多个缓存子单元。作为举例,每个缓存子单元大小为1kb,而每个缓存单元的大小为4kb。显然,缓存单元与缓存子单元可具有其他的尺寸。优选地,缓存子单元的大小等于主机发送给固态存储设备的io命令的最小数据单元大小,而缓存单元的大小为ftl表中的一个条目的物理地址所对应的数据单元大小。根据本申请的实施例,通过比较io命令的逻辑地址与元数据中记录的逻辑地址,确定缓存单元是否命中。作为另一个例子,元数据中记录物理地址,通过比较io命令的物理地址与元数据中记录的物理地址,确定缓存单元是否命中。缓存单元存储io命令所对应的数据。例如,对于写命令,缓存单元记录主机发来的要写入nvm芯片的数据,并在写命令的数据写入缓存单元后向主机提供写命令处理完成的指示,以降低写命令处理延迟。可选地,缓存单元还可用作加速读操作的高速缓存。实施例四图5展示了根据本申请实施例的缓存单元的状态图。缓存单元的每个可处于多种不同状态。元数据记录各个缓存单元的状态、缓存单元对应的逻辑地址、缓存单元被借用的情况、和/或缓存单元的缓存子单元被使用情况。参看图5,缓存单元的状态,包括“空闲”、“占用”和“淘汰”。可选地,还可以包括“忙碌”状态。其中,“空闲”状态指示的是该缓存单元未被使用,“空闲”状态的缓存单元中未缓存有效数据。当向“空闲”状态的缓存单元写入了数据之后,缓存单元变为“占用”状态,以指示缓存单元中已经存储了数据。可选地,由于写入数据过程“占用”一定时间,因而,由“忙碌”状态指示已开始向缓存单元写入数据但写入数据的过程尚未完成的状态。另外,将“占用”状态的缓存单元所缓存的数据写入nvm芯片的过程称为“淘汰”。响应于“淘汰”过程开始,缓存单元进入“淘汰中”状态。响应于缓存单元“淘汰”过程的结束,缓存单元所缓存的数据被写入nvm芯片,缓存单元重新进入“空闲”状态。“淘汰”过程也称为“清空”过程。实施例五图6展示了根据本申请实施例的缓存单元借用的示意图。也参看图4,cpu0通过维护元数据0管理缓存单元402、404、406与408,cpu1通过维护元数据1管理缓存单元412、414、416与418。在图6中,为处理io命令,cpu0需要使用原属于cpu1的缓存单元412与414。cpu0向cpu1发送消息以请求获得缓存单元412与414。cpu1修改将元数据1修改为元数据1’,以记录缓存单元412与414被借用,cpu1临时丧失对缓存单元412与414的使用权。以及响应于cpu1的对出借缓存单元的确认,cpu0也修改元数据0得到元数据0’,以通过元数据0’维护缓存单元412与414。根据本申请的实施例,在使用完缓存单元412与414,cpu0还将其归还cpu1。为归还缓存单元,cpu0与cpu1还修改各自的元数据,以记录对缓存单412与414元的归还。在一种实施方式中,多个cpu(cpu0、cpu1、cpu2与cpu3)具有顺序。cpui仅从cpui+1借用缓存单元(i取0、1或2)。而排序最后的cpu(例如,cpu3)仅从排序最前的cpu(例如,cpu0)借用缓存单元。以及cpu仅向出借缓存单元的cpu归还缓存单元。实施例六图7是根据本申请实施例的处理写命令的流程图。也参看图2,分配器230从主机接收到来自主机的写命令,依据写命令所访问的逻辑地址,将写命令分配给用于处理缓存任务的cpu之一(参看图7,步骤710)。作为举例,写命令访问的逻辑地址范围完全落入(包含于)cpu0所管理的逻辑地址范围,因而分配器230将该写命令分配给cpu0处理。接下来,cpu0在dram110(也参看图2)为写命令分配缓存单元(参看图7,步骤720)。cpu0依据写命令访问的逻辑地址范围与大小,确定所需的缓存单元数量。在一些情况下,写命令访问的逻辑地址范围小于一个缓存单元所指示的范围。例如,缓存单元容纳4kb逻辑地址的范围,而写命令向该4kb范围中的2kb写入数据。分配一个缓存单元即可容纳该写命令。在又一些情况下,写命令访问的逻辑地址范围(例如,128kb)大于缓存单元的逻辑地址范围(例如,4kb),在此情况下,将写命令拆分为多个子命令,每个子命令所访问的逻辑地址范围不超过一个缓存单元的逻辑地址范围。例如,写命令访问0-7kb的逻辑地址范围,为写命令分配两个缓存单元,第一个缓存单元用于容纳0-3kb逻辑地址范围的数据,而第二个缓存单元用于容纳4-7kblba范围的数据。作为另一个例子,写命令访问2-9kb的逻辑地址范围,为写命令分配三个缓存单元,第一个缓存单元用于容纳2-3kb逻辑地址范围的数据,而第二个缓存单元用于容纳4-7kb逻辑地址范围的数据,第三个缓存单元用于容纳8-9kb逻辑地址范围的数据。类似地,也可为读命令分配缓存单元。其中,缓存单元所对应的逻辑地址(即,缓存单元的元数据所指示的逻辑地址)范围均按例如4kb对齐(其起始地址位于4kb的整数倍地址处,例如,0、4kb、8kb),缓存单元所对应的逻辑地址空间大小为例如4kb。原子写命令的逻辑地址范围的大小同缓存单元的大小(例如4kb)可以不同。在根据本申请的实施例中,按写命令的逻辑地址范围,将写命令分为一个或多个子命令,每个子命令所访问的逻辑地址范围不超过一个缓存单元所对应的逻辑地址范围。以及为每个子命令分配一个缓存单元。作为举例,写命令访问1kb-10kb的逻辑地址空间,而每个缓存单元对应4kb地址空间。将写命令拆分成子命令s1、子命令s2与子命令s3。子命令s1访问1kb-3kb的大小为3kb逻辑地址范围,子命令s2访问4kb-7kb的大小为4kb的逻辑地址范围,子命令s3访问8kb-10kb的大小为3kb的地址范围。可选地,写命令所对应的逻辑地址空间无需连续,以及子命令的逻辑地址空间也无需连续。可选地,为分配缓存单元,cpu0还检查缓存单元的状态。分配给写命令或其子命令的缓存单元可以是该写命令或其子命令所命中的缓存单元,在未命中任何缓存单元的情况下,为该写命令或其子命令(统称“写命令”)申请缓存单元。接下来,通过比较写命令的逻辑地址与缓存单元元数据中记录的逻辑地址,来确定缓存单元是否命中。若写命令的逻辑地址同缓存单元的元数据记录的逻辑地址相同,或写命令的逻辑地址范围被缓存单元的元数据记录的逻辑地址范围所包含,则该写命令命中该缓存单元。其中,为写命令申请的缓存单元可以是尚未被写入数据的处于“空闲”状态的缓存单元,也可以是已被写入数据的处于“占用”、“忙碌”或“淘汰”中的缓存单元。若缓存单元未命中,为申请缓存单元,将所申请的缓存单元中的数据通过“淘汰”过程写入nvm芯片,再将被清空的缓存单元分配给写命令。可选地,若因等待“淘汰”过程或其他操作完成而暂时不能使用缓存单元,暂停对写命令的处理,例如,将写命令加入等待队列。可以理解地,若写命令被拆分为多个子命令,这些子命令可以全部命中缓存单元,也可以是一部分子命令命中缓存单元,而另外一部分子命令未命中缓存单元,并且为未命中缓存单元的子命令申请缓存单元。在一个实施方式中,为了方便为未命中任何缓存单元的子命令分配缓存单元,为处于“空闲”状态的缓存单元建立缓存单元池,缓存单元池中均是处于“空闲”状态的缓存单元。当子命令未命中任何缓存单元时,从该缓存单元池中获取缓存单元,由此能够方便地为子命令分配缓存单元。更进一步地,可以将被清空的缓存单元归还该缓存单元池。接下来,在为写命令分配了缓存单元之后,将该写命令要写入的数据写入所分配的缓存单元(参看图7,步骤730)。例如,在主机与存储设备之间发起dma操作,将要写入的数据从主机搬移到dram的缓存单元。响应于该写命令要写入的数据被全部写入缓存单元,向主机指示写命令处理完成(参看图7,步骤740)。此时,尽管写命令所对应的数据可能尚未被写入nvm芯片,但只要这些数据被写入到了缓存单元中,则通知主机,该写命令处理完成。这有利于降低写命令处理的延迟。可选地,还对缓存单元主动发起“淘汰”过程,以将被写入数据的缓存单元释放,使其成为处于“空闲”状态的缓存单元。实施例七图8是根据本申请又一实施例的处理写命令的流程图。分配器230从主机接收到来自主机的写命令,依据写命令所访问的逻辑地址,将写命令分配给用于处理缓存任务的cpu之一(参看图8,步骤810)。作为举例,写命令访问的逻辑地址范围完全落入cpu0所管理的逻辑地址范围,因而分配器230将该写命令分配给cpu0处理。作为又一个例子,写命令访问的逻辑地址范围落入了cpu0所管理的逻辑地址范围(例如,区域302)以及cpu1所管理的逻辑地址范围(例如,区域304)(也参看图3),分配器230将该写命令分配给管理其访问的逻辑地址范围的cpu0与cpu1之一处理。作为举例,分配器230选择两个或多个cpu中,所管理的逻辑地址范围排序在前的那个cpu(例如,cpu0)来处理该写命令。接下来,cpu0检查要处理的写命令的逻辑地址范围是否超出了自己所管理的逻辑地址范围(参看图8,步骤820)。若写命令的逻辑地址范围完全落入(包含于)自身所管理的逻辑地址范围,cpu0在dram中为写命令分配缓存单元(参看图8,步骤830),将写命令对应的数据写入所分配的缓存单元(参看图8,步骤832),以及向主机指示写命令处理完成(参看图8,步骤834)。若写命令的逻辑地址范围超越了cpu0自身所管理的逻辑地址范围,cpu0向其他cpu请求临时管理写命令所需的逻辑地址范围(参看图8,步骤840)。例如,写命令还要访问逻辑地址区域304(也参看图3),cpu0向cpu1请求用于区域304的一个或多个缓存单元。根据本申请的实施例,为了请求缓存单元,cpu0向cpu1提供需要访问的属于区域304(也参看图3)的逻辑地址范围。cpu1根据所接收的逻辑地址范围分配一个或多个缓存单元(参看图8,步骤842),并在cpu1的元数据1中记录这些缓存单元被“借用”(给cpu0)。可选地,cpu0从借用的缓存单元中分配缓存单元。可选地,为出借缓存单元,cpu1还检查缓存单元的状态。出借的缓存单元可以是该逻辑地址范围所命中的缓存单元。在未命中任何缓存单元的情况下,为该逻辑地址范围申请缓存单元。cpu1还向cpu0指示借用给cpu0的缓存单元,例如,指示缓存单元在dram中的存储位置,以及缓存单元的状态。通过例如为被出借的缓存单元的元数据加锁,使得cpu1不能使用被出借的缓存单元,也不能再将这些缓存单元借给其他cpu。可选地,若被“借用”的缓存单元是已被写入数据的处于“占用”、“忙碌”或“淘汰”中的缓存单元(参看图5),cpu0或者cpu1还在这些缓存单元上发起“淘汰”过程,以使这些缓存单元变为“空闲”状态(也参看图5)。可选地,cpu0响应于cpu1的应答,在元数据0(参看图4)中记录获得的缓存单元,并将“借用”的缓存单元用作分配给写命令的缓存单元。接下来,cpu0将该写命令要写入的数据写入所分配的缓存单元(参看图8,步骤844)。响应于该写命令要写入的数据被全部写入缓存单元,向主机指示写命令处理完成。可以理解地,一些写命令使用多个缓存单元,在将写命令的全部数据都写入缓存单元后,才向主机指示写命令处理完成(参看图8,步骤848)。可选地,在将写命令的全部数据都写入缓存单元后,cpu0还将借用的缓存单元归还cpu1。cpu0向cpu1指示所归还的缓存单元。cpu1响应于来自cpu0的指示,在元数据1中更新被归还的缓存单元的状态(参看图8,步骤846),从而cpu1重新拥有这些缓存单元的使用权,可使用或再次出借这些缓存单元(例如,对缓存单元的元数据解锁)。cpu1还向cpu0确认缓存单元的归还,以及cpu0在元数据0中清除这些缓存单元,或标记这些缓存单元已被归还。从而cpu0不再拥有这些缓存单元的使用权。可选的,为归还缓存单元,cpu0向cpu1指示的是缓存单元的元数据信息(例如,缓存单元在dram中的地址)。被归还的缓存单元中可能还存储有被写入的数据,并处于“占用”、“忙碌”或“淘汰”状态。cpu1依据cpu0提供的元数据信息,继续对缓存单元进行管理。实施例八图9是根据本申请实施例的处理读命令的流程图。分配器230从主机接收收到来自主机的读命令,依据读命令所访问的逻辑地址,将读命令分配给用于处理缓存任务的cpu之一(参看图9,步骤910)。作为举例,读命令访问的逻辑地址范围完全落入(属于)cpu0所管理的逻辑地址范围,因而分配器230将该写命令分配给cpu0处理。作为又一个例子,读命令访问的逻辑地址范围落入了cpu0所管理的逻辑地址范围(例如,区域302)以及cpu1所管理的逻辑地址范围(例如,区域304)(也参看图3),分配器230将该读命令分配给管理其访问的逻辑地址范围的cpu0与cpu1之一处理。接下来,cpu0检查要处理的读命令的逻辑地址范围是否超出了自己所管理的逻辑地址范围(参看图9,步骤920)。若读命令的逻辑地址范围完全落入自身所管理的逻辑地址范围,则继续检查读命令是否命中了cpu0所管理的缓存单元(参看图9,步骤930)。通过比较读命令的逻辑地址范围与缓存单元的逻辑地址来识别读命令是否命中缓存单元。可以理解地,读命令可被拆分为多个子命令,每个子命令的逻辑地址范围不超过一个缓存单元所对应的逻辑地址范围。若读命令或其子命令(以下统称“读命令”)命中了缓存单元,从缓存单元中获取读命令所访问的数据,并提供给主机(参看图9,步骤932)。例如,通过在dram110与主机之间发起dma传输。若读命令未命中缓存单元,则根据读命令的逻辑地址范围获取对应的物理地址(参看图9,步骤940),并根据物理地址从nvm芯片中读出数据并提供给主机(参看图9,步骤942)。以及可选地,还为读命令分配缓存单元,并用从nvm芯片读出的数据替换缓存单元中的数据(参看图9,步骤944)。而若读命令的逻辑地址范围超出了cpu0自身所管理的逻辑地址范围,cpu0向其他cpu请求临时管理读命令所需的逻辑地址范围(参看图9,步骤950)。为了请求缓存单元,cpu0向cpu1提供需要访问的属于区域304(也参看图3)的逻辑地址范围。接下来,cpu1检查所接收的逻辑地址范围是否命中了一个或多个缓存单元(参看图9,步骤960)。以及cpu1将命中的缓存单元的元数据(包括,在dram中的地址,状态等)发送给cpu0。若cpu1所接收的部分或全部逻辑地址范围未命中缓存单元,向cpu0提供逻辑地址范围未命中缓存单元的指示。对于命中的缓存单元(无论是cpu0自己维护的还是从cpu1借用的),cpu0从缓存单元中获取读命令要访问的数据,并提供给主机(参看图9,步骤962)。对于未命中缓存单元的逻辑地址范围(来自读命令或读命令的子命令),则根据读命令的逻辑地址范围获取对应的物理地址(参看图9,步骤970),并根据物理地址从nvm芯片中读出数据并提供给主机(参看图9,步骤972)。以及可选地,响应于cpu0请求缓存单元的逻辑地址范围,对于未命中缓存单元的逻辑地址范围,cpu1也为其分配缓存单元,并将所分配的缓存单元的元数据发送给cpu0。cpu0响应于缓存单元未命中,从nvm芯片读出数据并提供给主机,以及用从nvm芯片读出的数据替换缓存单元中的数据(参看图9,步骤974),再将缓存单元归还cpu1(参看图9,步骤964)。实施例九图10是根据本申请实施例的掉电处理的流程图。根据本申请的实施例,在“占用”状态的缓存单元中存储了尚未被写入nvm芯片但已向主机确认写命令处理完成的数据(也参看图5)。在固态存储设备遭遇意外掉电时,需要备份缓存单元中的数据,以及还需要备份缓存单元的元数据,以在恢复了备份数据后,能再次使用缓存单元。当发生异常掉电,各个cpu会收到对异常掉电的指示。各cpu终止尚未处理完成(例如,尚未向主机指示处理完成)的读/写命令的处理,并开始掉电处理流程。在掉电处理流程中,各cpu要将各自的需要备份的缓存单元及其元数据写入nvm芯片的日志区。处于“占用”状态的缓存单元是需要备份的。而处于“空闲”状态的缓存单元因不含有有效数据而无需备份。对于处于“忙碌”状态的缓存单元,其中的数据对应于尚未向主机确认的写命令的数据,因而无须备份。对于处于“淘汰中”状态的缓存单元,可等待淘汰过程完成,缓存单元变为“空闲”状态,而无须备份;也可停止淘汰过程,而将缓存单元的状态设为“占用”,并且需要对其备份。可以理解地,在其他实施例中,可为缓存单元维护其他状态,处于其他状态的缓存单元可能需要备份或无需备份(也参看图5)。参看图10,若cpu各自的元数据中有从其他cpu借用的元数据,在掉电流程开始后,首先归还借用的元数据。例如,cpu0将从cpu1借用的元数据归还cpu1(参看图10,步骤p1),cpu1将从cpu2借用的元数据归还cpu2(参看图10,步骤p2),cpu2将从cpu0借用的元数据归还cpu0(参看图10,步骤p3)。借用的元数据,是指示借用的缓存单元的元数据,其中包括借用的缓存单元的在dram110中的地址以及缓存单元的状态。以cpu0为例,响应于收到cpu2返还的元数据,cpu0通过自身的元数据0(也参看图4)可识别自身需要备份的缓存单元的数量(参看图10,步骤p3)。需要备份的缓存单元,例如是处于“占用”状态的缓存单元。cpu0将自身需要备份的缓存单元的数量通知多个cpu的排序中的下一cpu(例如,cpu1)(参看图10,步骤p4)。告知下一cpu自身需备份的缓存单元的数量,目的在于使下一cpu知晓用于存储待备份的缓存单元的日志区或存储空间的起始地址。根据本申请的实施例中,多个cpu共享日志区。多个cpu中排序最前的cpu(例如,cpu0)将日志区的指定位置作为备份缓存单元的起始地址。而cpu1根据cpu0提供的需要备份的缓存单元数量,计算出cpu0用于备份缓存单元所需的缓冲区大小,并确定自身在日志区中备份缓存单元的起始地址。而cpu1将所收到的需要备份的缓存单元数量以及自身所要备份的缓存单元数量累加,并告知多个cpu中的下一cpu(例如,cpu2)。以此方式,每个cpu都将知晓自身在日志区中备份缓存单元的起始地址。多个cpu中的最后cpu(例如,图10中的cpu2)识别要备份的存储单元并依据从前一cpu(例如,cpu1)获取的待备份的存储单元数量确定在日志区中备份缓存单元的起始地址,并备份缓存单元(参看图10,步骤p5),而无须识别或累积待备份的存储单元数量并发送给其他cpu。知晓自身在日志区中备份缓存单元的起始地址后,cpu对缓存单元进行备份,例如将要备份的缓存单元内容及其元数据写入nvm芯片。可选地,用于处理缓存任务的cpu将要备份的缓存单元及其元数据备份在dram110的指定存储空间。再将dram110的指定存储空间整体备份到日志区。用于处理缓存任务的各个cpu,都完成对缓存单元的备份后,本申请实施例的掉电处理流程完成。例如,各个cpu在完成对缓存单元的备份后,告知下一cpu,而多个cpu中排序最后的cpu(例如,cpu2)确认用于处理缓存任务的所有cpu的备份完成(参看图10,步骤p6或步骤p7)。作为另一个例子,指定cpu2收集缓存单元的备份进度。其他各个cpu在完成缓存单元备份后,告知cpu2,使得cpu2知晓多个cpu的备份进度,并确认备份完成。实施例十固态存储设备从主机接收io命令。io命令可指示其为原子操作。或者,主机可指示固态存储设备在处理io操作时,满足原子性要求,例如,在nvme协议中定义的一般原子性和/或掉电原子性。nvme协议的掉电原子性(awupf,atomicwriteunitpowerfail)要求,固态存储设备确保,如果因掉电或其他错误条件导致命令处理失败,那么对关联于失败命令的逻辑地址的后续读命令将得到:(1)所有的旧数据(被打断的写命令访问的逻辑地址上的原始数据);或者(2)所有的新数据(被打断的写命令所写入的全部数据)。nvme协议的一般原子性(awun,atomicwriteunitnormal)定义了命令执行相对于其他命令的原子性,确保写命令相对于其他读命令或写命令具有原子性。除了要求写入nvm芯片的数据不会同时包含新命令的部分数据与新命令之外的其他命令的部分数据,还需要保证主机发出的读命令读到的数据中不会同时包含新命令的部分数据与新命令之外的其他命令的部分数据。图11是根据本申请实施例的处理需要满足原子性的写命令(简称为“原子写命令”)流程图。固态存储设备从主机接收原子写命令。依据访问的逻辑地址范围,将原子写命令拆分为多个子命令,使得每个子命令访问的逻辑地址范围不超过一个缓存单元的逻辑地址范围。接下来,获取待处理的子命令(参看图11,步骤1110)。子命令可能来自于等待队列,或者拆分原子写命令所得到的子命令。对于获取的子命令,检查其是否是所属的写命令的多个尚未处理的子命令中,按逻辑地址排序最前的子命令。仅当获取的子命令是所属的写命令的多个尚未处理的子命令中,按逻辑地址排序最前的子命令时,才对该子命令进行处理。为处理该子命令,为该子命令分配缓存单元,以及对分配的缓存单元加锁(参看图11,步骤1120)。被加锁的缓存单元不能再用于服务对其他原子写命令的处理,也不能被分配给其他缓存单元。在加锁操作成功之前,不对该子命令进行处理,也不对该原子写命令的排序在该子命令之后的其他子命令进行处理。若为子命令分配分配缓存单元失败,例如,缓存单元都被加锁,缓存单元正处于“淘汰中”状态,或者缓存单元已被加锁,暂停对该子命令的处理,例如,将子命令或其所属的写命令加入等待队列。响应于加锁成功,对子命令进行处理,例如,发起dma传输,将子命令对应的数据从主机传送到缓存单元,以及将缓存单元的状态设置为“占用”或“忙碌”,还在缓存单元的元数据中记录子命令所访问的逻辑地址范围(参看图11,步骤1130)。接下来,判断是否已为该原子写命令的所有子命令对应的缓存单元全部加锁(参看图11,步骤1140)。若未全部加锁,则按照未被处理的多个子命令的逻辑地址的排序,获取下一个子命令(参看图11,步骤1110)。若为该原子写命令的所有子命令都分配了缓存单元且对应的缓存单元已被全部加锁,则可继续完成对这些多个子命令的处理(参看图11,步骤1150),例如将子命令对应的数据从主机搬移到缓存单元,以及在该原子写命令的所有子命令对应的数据都写入缓存单元后,向主机指示该原子写命令处理完成。在该原子写命令的所有子命令对应的数据都写入缓存单元后,释放分配给该原子写命令的所有缓存单元的锁(参看图11,步骤1160),从而这些缓存单元可被分配给其他原子写命令。可选地,步骤1130与步骤1140的顺序可以交换。在步骤1130,为排序在前的子命令的缓存单元加锁后,可直接通过步骤1140判断是否有其他子命令待处理。并返回步骤1110与步骤1120为排序的多个子命令中的下一子命令分配缓存单元。而对其缓存单元加锁成功的一个或多个子命令,通过执行步骤1130对子命令进行处理。而步骤1160,则需要发生在步骤1140中判断出已经为该原子写命令的所有子命令对应的缓存单元全部加锁之后。在根据本申请的实施例十中,处理每一个原子写命令时,满足两个条件:(1)按原子写命令的多个子命令的逻辑地址的值的顺序,为每个子命令分配缓存单元并对缓存单元加锁,仅在加锁成功后,才处理按逻辑地址的值排序的下一子命令;(2)在依据原子写命令的所有子命令将数据都写入缓存单元后,才释放同该原子写命令的所有子命令对应的缓存单元的锁。可选地,若在处理原子写命令期间,有待处理的原子读命令或其子命令,则在处理原子读命令时,无须检查相关缓存单元是否被加锁,也无须为处理原子读命令或其子命令而对相关缓存单元加锁。依然可选地,在处理原子命令时,也可在获得锁的情况下,才对原子读命令进行处理。可选地,为对原子写命令的多个子命令按逻辑地址顺序排序,可以按逻辑地址数值的升序排序,也可以按逻辑地址数值的降序排序。无论采用哪种方式作为排序的依据,对于处理的多个原子写命令,使用相同的排序方式。在根据本申请的实施例中,在满足上述两个条件的情况下,可以对多个原子写命令的多个子命令并行处理。可选地,若原子写命令指示要访问的物理地址,将根据图11的实施例中对逻辑地址的操作相应替换为物理地址。实施例十一图12是根据本申请又一实施例的处理需要满足原子性的写命令流程图。分配器230(也参看图2)从主机接收到来自主机的原子写命令,依据原子写命令所访问的逻辑地址,将原子写命令分配给用于处理缓存任务的cpu之一(参看图12,步骤1210)。作为例子,原子写命令访问的逻辑地址范围落入(小于或等于)了cpu0所管理的逻辑地址范围(例如,区域302)以及cpu1所管理的逻辑地址范围(例如,区域304)(也参看图3),分配器230将该原子写命令分配给管理其访问的逻辑地址范围的cpu0与cpu1之一处理(例如,cpu0)。接下来,cpu0依据访问的逻辑地址范围,将原子写命令拆分为多个子命令。每次获取属于一原子写命令的未被处理的多个子命令中排序在最前的子命令进行处理(参看图12,步骤1220)。若获取的子命令并非排序在最前的子命令,暂停对该子命令的处理,例如,将其加入等待队列。接下来,cpu0检查要处理的子命令的逻辑地址范围是否超出了自己所管理的逻辑地址范围(参看图12,步骤1230)。若子命令的逻辑地址范围完全落入自身所管理的逻辑地址范围,cpu0在dram中为子命令分配缓存单元,为所分配的缓存单元加锁(参看图12,步骤1240)。响应于加锁成功,将子命令对应的数据写入所分配的缓存单元(参看图12,步骤1250)。若子命令的逻辑地址范围超越了cpu0自身所管理的逻辑地址范围,cpu0向其他cpu请求临时管理写命令所需的逻辑地址范围(参看图12,步骤1232)。例如,子命令要访问逻辑地址区域304,cpu0向cpu1请求用于区域304的缓存单元。在从cpu1获得了缓存单元后,cpu0将该缓存单元分配给子命令,为所分配的缓存单元加锁(参看图12,步骤1240),响应于加锁成功,将子命令对应的数据写入所分配的缓存单元(参看图12,步骤1250)。为分配缓存单元,还cpu0还检查缓存单元的状态(也参看图5)。若子命令的逻辑地址范围命中了缓存单元,则为子命令分配命中的缓存单元。在未命中任何缓存单元的情况下,为该写命令或其子命令(统称“写命令”)申请缓存单元。接下来,判断是否已为该原子写命令的所有子命令对应的缓存单元全部加锁(参看图12,步骤1260)。若未全部加锁,获取属于同一原子写命令的未被处理的多个子命令的逻辑地址的排序最前的下一子命令并处理该下一个子命令(参看图12,步骤1220)。若为该原子写命令的所有子命令都分配了缓存单元且对应的缓存单元已被全部加锁,响应于所有子命令所对应的数据都被写入缓存单元,向主机指示该原子写命令处理完成(参看图12,步骤1280)。在该原子写命令的所有子命令对应的数据都写入缓存单元后,释放分配给该原子写命令的所有缓存单元的锁(参看图12,步骤1270),从而这些缓存单元可被分配给其他写命令。以及对于从其他cpu借用的缓存单元,在缓存单元的锁被释放后,cpu0向其他cpu归还所借用的缓存单元(参看图12,步骤1290)。可以理解的,为归还缓存单元,cpu0向cpu1指示的是缓存单元的元数据信息(例如,缓存单元在dram中的地址)。被归还的缓存单元中可能还存储有被写入的数据,并处于“占用”、“忙碌”或“淘汰”状态。cpu1依据cpu0提供的元数据信息,继续对缓存单元进行管理(也参看图4)。可选地,若原子写命令指示要访问的物理地址,将根据图12的实施例中对逻辑地址的操作相应替换为物理地址。实施例十二图13是根据本申请实施例的原子命令的示意图。图14与图15是处理图13的原子写命令过程中的缓存单元的示意图。参看图13,固态存储设备从主机接收到原子写命令a与原子写命令b。原子写命令a包括3个子命令(x(t1),x+1(t5)与x+2(t3)),原子写命令b包括3个子命令(x(t4),x+1(t2)与x+2(t6))。在图13中,由每个方框指示子命令,例如,用x(t1)表示其中一个子命令,x指示子命令访问的逻辑地址,t1指示获取该子命令的时间,以及数字的大小指示了时间先后顺序。t1时刻,获取了原子写命令a的子命令x(t1)。按逻辑地址顺序处理原子写命令a的多个子命令。由于子命令x(t1)是原子写命令a的尚未被处理的多个子命令中逻辑地址排序最前的子命令,可以对子命令x(t1)进行处理。根据逻辑地址x申请到缓存单元910,对缓存单元910加锁(也参看图11,步骤1120,或者参看图12,步骤1240)。图14中,缓存单元1410对应的锁a(t1)指示该缓存单元的锁属于原子写命令a,还在缓存单元1410的元数据中记录其逻辑地址为x。可以理解地,在元数据中记录的锁可以仅指示锁的存在性,而不指示该锁所属的对象。可选地,为申请缓存单元1410以及对缓存单元1410加锁,在缓存单元1410上发起淘汰过程,缓存单元1410转变为“空闲”状态(也参看图5)。t2时刻,获取了原子写命令b的子命令x+1(t2)。按逻辑地址顺序处理原子写命令b的多个子命令。由于原子写命令b的多个子命令中,逻辑地址排序在前的子命令x(t4)尚未被处理,此时不能开始处理子命令x+1(t2)。t3时刻,获取了原子写命令a的子命令x+2(t3)的数据。按逻辑地址顺序处理原子写命令a的多个子命令。由于原子写命令a的多个子命令中,逻辑地址排序在前的子命令x+1(t5)尚未被处理,此时不能开始处理子命令x+2(t3)。t4时刻,获取了原子写命令b的子命令x(t4)。按逻辑地址顺序处理原子写命令b多个子命令。子命令x(t4)是原子写命令b的尚未被处理的多个子命令中,逻辑地址排序最前的子命令,因而可以处理子命令x(t4)。为子命令x(t4)申请缓存单元。由于子命令x(t4)访问逻辑地址x,其命中了缓存单元1410,但此时,该缓存单元1410被加锁a(t1),因而为子命令x(t4)请求缓存单元1410的锁失败,此时不能开始处理子命令x(t4)。t5时刻,收到原子写命令a的子命令x+1(t5)。按逻辑地址顺序处理原子写命令a的多个子命令。由于子命令x+1(t5)是原子写命令a尚未被处理的多个子命令中排序最前的子命令,因而为子命令x+1(t5)申请到缓存单元1412,对缓存单元1412加锁(也参看图11,步骤1120,或者参看图12,步骤1240)。缓存单元1412对应的锁a(t5)指示该缓存单元的锁属于原子写命令a。由于为原子写命令a的按逻辑地址排序的第2个子命令x+1(t5)申请到锁,接下来可以处理原子写命令a的第3个子命令x+2(t3)。为子命令x+2(t3)申请缓存单元1414,并对缓存单元1414加锁(也参看图11,步骤1120;或者参看图12,步骤1240)。至此,原子写命令a的所有子命令都申请了缓存单元,并对缓存单元都加锁成功。在对原子写命令a的所有子命令所对应的数据都被写入各个缓存单元后(也参看图11,步骤1150),向主机指示该原子写命令a处理完成(参看图12,步骤1280),释放分配给该原子写命令a的所有缓存单元的锁(也参看图11,步骤1160,或者参看图12,步骤1270),从而这些缓存单元可被分配给其他写命令。接下来,获取原子写命令b的子命令x(t4),按逻辑地址顺序处理原子写命令b的多个子命令。由于其是原子写命令b的多个子命令中逻辑地址排序最前的子命令,为子命令x(t4)申请缓存单元1410,并加锁成功(参看图15的锁b(t4))(也参看图11,步骤1120,或者参看图12,步骤1240)。由于为原子写命令b的第1个子命令x(t4)的缓存单元申请到锁,接下来可以处理原子写命令b的第2个子命令x+1(t2),为其申请到缓存单元1412,并加锁成功(参看图15的锁b(t2))(也参看图11,步骤1120,或者参看图12,步骤1240)。接下来在t6时刻获取到原子写命令b的子命令x+2(t6)。为子命令x+2(t6)申请到缓存单元1414并加锁成功(参看图15的锁b(t6))(也参看图11,步骤1120,或者参看图12,步骤1240)。至此,原子写命令b的所有子命令都申请了缓存单元,并对缓存单元都加锁成功。在对原子写命令b的所有子命令所对应的数据都被写入各个缓存单元后(也参看图11,步骤1150),向主机指示该原子写命令b处理完成(也参看图12,步骤1280),释放分配给该原子写命令b的所有缓存单元的锁(也参看图11,步骤1160,或者参看图12,步骤1270)。参看表2,表2的第二行示出了原子写命令a执行完成后的有效结果:在逻辑地址lba(x)、lba(x+1)与lba(x+2)中分别是原子写命令a所写入的数据x(t1)(这里用子命令x(t1)指示该子命令所写入的数据),x+1(t5)和x+2(t3)。表2的第三行示出了原子写命令b执行完成后的有效结果:在逻辑地址lba(x)、lba(x+1)与lba(x+2)中分别是原子写命令b所写入的数据x(t4),x+1(t2)和x+2(t6)。因而,确保了在逻辑地址x到x+2范围内,不会出现部分逻辑地址是原子写命令a写入的数据而部分逻辑地址是原子写命令b写入的数据的情形,实现了原子写命令处理的原子性。表2实施例十三图16是根据本申请又一实施例的原子写命令的示意图。图17、图18与图19是处理图16的原子写命令过程中的缓存单元的示意图。参看图16,固态存储设备从主机接收的原子写命令c、原子写命令d与原子写命令e。原子写命令c被拆分为3个子命令(x(t1),x+1(t5)与x+2(t6)),原子写命令d被分为3个子命令(x(t7),x+1(t8)与x+2(t9)),原子写命令e被分为3个子命令(x+1(t2)、x+2(t3)与x+3(t4))。t1时刻,获取了原子写命令c的子命令x(t1)。按逻辑地址顺序处理原子写命令c的多个子命令。由于子命令x(t1)是原子写命令c的尚未被处理的多个子命令中逻辑地址排序最前的子命令,可以对子命令x(t1)进行处理。根据逻辑地址x申请到缓存单元1710,对缓存单元1710加锁(也参看图11,步骤1120,或者参看图12,步骤1240)。图17中,缓存单元1710对应的锁c(t1)指示该缓存单元的锁属于原子写命令c,还在缓存单元1710的元数据中记录其逻辑地址为x。t2时刻,获取了原子写命令e的子命令x+1(t2)。按逻辑地址顺序处理原子写命令e的多个子命令。由于子命令x+1(t2)是原子写命令e的尚未被处理的多个子命令中逻辑地址排序最前的子命令,可以对子命令x+1(t2)进行处理。根据逻辑地址x+1申请缓存单元1712,并对缓存单元1712加锁(参看图17)(也参看图11,步骤1120,或者参看图12,步骤1240)。图17中,缓存单元1712对应的锁e(t2)指示该缓存单元的锁属于原子写命令e,还在缓存单元1712的元数据中记录其逻辑地址为x+1。t3时刻,获取了原子写命令e的子命令x+2(t3)。按逻辑地址顺序处理原子写命令e的多个子命令。由于子命令x+2(t3)是原子写命令e的尚未被处理的最后一个的子命令,可以对子命令x+2(t3)进行处理。根据逻辑地址x+2申请缓存单元1714,并对缓存单元1714加锁(参看图17)(也参看图11,步骤1120,或者参看图12,步骤1240)。图17中,缓存单元1714对应的锁e(t3)指示该缓存单元的锁属于原子写命令e,还在缓存单元1714的元数据中记录其逻辑地址为x+2。t4时刻,获取了原子写命令e的子命令x+3(t4)。按逻辑地址顺序处理原子写命令e的多个子命令。由于子命令x+3(t4)是原子写命令e的尚未被处理的多个子命令中逻辑地址排序最前的子命令,可以对子命令x+3(t4)进行处理。根据逻辑地址x+3申请缓存单1716,并对缓存单元1716加锁(参看图17)(也参看图11,步骤1120,或者参看图12,步骤1240)。图17中,缓存单元1716对应的锁e(t4)指示该缓存单元的锁属于原子写命令e,还在缓存单元1716的元数据中记录其逻辑地址为x+3。至此,为原子写命令e的所有子命令都申请了缓存单元,并对缓存单元都加锁成功。在对原子写命令e的所有子命令所对应的数据都被写入各个缓存单元(也参看图11,步骤1150)后,向主机指示该原子写命令e处理完成(也参看图12,步骤1280),释放分配给该原子写命令e的所有缓存单元的锁(也参看图11,步骤1160,或者参看图12,步骤1270),从而这些缓存单元可被分配给其他写命令。t5时刻,获取了原子写命令c的子命令x+1(t5)。按逻辑地址顺序处理原子写命令c的多个子命令。由于子命令x+1(t5)是原子写命令c的尚未被处理的多个子命令中逻辑地址排序最前的子命令,可以对子命令x+1(t5)进行处理。根据逻辑地址x+1申请缓存单元1712,并对缓存单元1712加锁(参看图18)(也参看图11,步骤1120,或者参看图12,步骤1240)。图18中,缓存单元1712对应的锁c(t5)指示该缓存单元的锁属于原子写命令c,还在缓存单元1712的元数据中记录其逻辑地址为x+1。t6时刻,获取了原子写命令c的子命令x+2(t6)。按逻辑地址顺序处理原子写命令c的多个子命令。由于子命令x+2(t6)是原子写命令c的尚未被处理的多个子命令中逻辑地址排序最前的子命令,可以对子命令x+2(t6)进行处理。根据逻辑地址x+2申请缓存单元1714,并对缓存单元1714加锁(参看图18)(也参看图11,步骤1120,或者参看图12,步骤1240)。图18中,缓存单元1714对应的锁c(t6)指示该缓存单元的锁属于原子写命令c,还在缓存单元1714的元数据中记录其逻辑地址为x+2。至此,为原子写命令c的所有子命令都申请了缓存单元,并对缓存单元都加锁成功。在对原子写命令c的所有子命令所对应的数据都被写入各个缓存单元(也参看图11,步骤1150)后,向主机指示该原子写命令c处理完成(也参看图12,步骤1280),释放分配给该原子写命令c的所有缓存单元的锁,从而这些缓存单元可被分配给其他写命令(也参看图11,步骤1160,或者参看图12,步骤1270)。t7时刻,获取了原子写命令d的子命令x(t7)。按逻辑地址顺序处理原子写命令d的多个子命令。由于子命令x(t7)是原子写命令d的尚未被处理的多个子命令中逻辑地址排序最前的子命令,可以对子命令x(t7)进行处理。根据逻辑地址x申请缓存单元1710,并对缓存单元1710加锁(参看图19)(也参看图11,步骤1120,或者参看图12,步骤1240)。图19中,缓存单元1710对应的锁d(t7)指示该缓存单元的锁属于原子写命令d,还在缓存单元1710的元数据中记录其逻辑地址为x。t8时刻,获取了原子写命令d的子命令x+1(t8)。按逻辑地址顺序处理原子写命令d的多个子命令。由于子命令x+1(t8)是原子写命令d的尚未被处理的多个子命令中逻辑地址排序最前的子命令,对子命令x+1(t8)进行处理。根据逻辑地址x+1申请缓存单元1712,并对缓存单元1712加锁(参看图19)(也参看图11,步骤1120,或者参看图12,步骤1240)。图19中,缓存单元1712对应的锁d(t8)指示该缓存单元的锁属于原子写命令d,还在缓存单元1712的元数据中记录其逻辑地址为x+1。t9时刻,获取了原子写命令d的子命令x+2(t9)。按逻辑地址顺序处理原子写命令d的多个子命令。由于子命令x+2(t9)是原子写命令d的尚未被处理的多个子命令中逻辑地址排序最前的子命令,对子命令x+2(t9)进行处理。根据逻辑地址x+2申请缓存单元1714,并对缓存单元1714加锁(参看图19)(也参看图11,步骤1120,或者参看图12,步骤1240)。图19中,缓存单元1714对应的锁d(t9)指示该缓存单元的锁属于原子写命令d,还在缓存单元1714的元数据中记录其逻辑地址为x+2。至此,为原子写命令d的所有子命令都申请了缓存单元,并对缓存单元都加锁成功。在对原子写命令d的所有子命令所对应的数据都被写入各个缓存单元(也参看图11,步骤1150)后,向主机指示该原子写命令d处理完成(也参看图12,步骤1280),释放分配给该原子写命令d的所有缓存单元的锁,从而这些缓存单元可被分配给其他写命令(也参看图11,步骤1160,或者参看图12,步骤1270)。参看表3,表3的第二行原子写命令e执行完成后的有效结果:在逻辑地址lba(x+1)、lba(x+2)与lba(x+3)中分别是原子写命令e所写入的数据x+1(t2)、x+2(t3)和x+3(t4),而在逻辑地址lba(x)中则是原子写命令c所写入的数据x(t1)。表3的第三行示出了原子写命令c执行完成后有效的结果:在逻辑地址lbax、lba(x+1)与lba(x+2)中分别是原子写命令c所写入的数据x(t1),x+1(t5)和x+2(t6),而在逻辑地址lba(x+3)处则保留了原子写命令e所写入的数据x+3(t4)。表3的第四行示出了原子写命令d执行完成后的有效结果:在逻辑地址lba(x)、lba(x+1)与lba(x+2)中分别是原子写命令d所写入的数据x(t7),x+1(t8)和x+2(t9),而在逻辑地址lba(x+3)处则保留了原子写命令e所写入的数据x+3(t4)。表3根据结合图7-图19的本申请的实施例,可选地,若在处理原子写命令期间,有待处理的原子读命令或其子命令,则在处理原子读命令时,无须检查相关缓存单元是否被加锁,也无须为处理原子读命令或其子命令而对相关缓存单元加锁。可选地,在处理原子读命令时,也可在获得锁的情况下,才对原子读命令进行处理。通过以上面公开的方式处理原子写命令,能够满足nvme协议中对掉电原子性(awupf,atomicwriteunitpowerfail)的要求,保障在掉电或其他错误条件打断了写操作时,固态存储设备对写操作的处理行为。固态存储设备确保,如果因掉电或其他错误条件导致命令处理失败,那么对关联于失败命令的逻辑地址的后续读命令将得到:(1)所有的旧数据(被打断的写命令访问的逻辑地址上的原始数据);或者(2)所有的新数据(被打断的写命令所写入的全部数据)。实施例十四nvme规范中还定义了一般原子性(awun,atomicwriteunitnormal)。一般原子性定义了命令执行相对于其他命令的原子性,确保写命令相对于其他读命令或写命令具有原子性。除了要求写入nvm芯片的数据不会同时包含新命令的部分数据与新命令之外的其他命令的部分数据,还需要保证主机发出的读命令读到的数据中不会同时包含新命令的部分数据与新命令之外的其他命令的部分数据。在根据本申请的实施例中,固态存储设备通过同时实现读命令的原子处理与写命令的原子处理来实现符合nvme规范要求的一般原子性(awun)。图20是根据本申请实施例的处理需要满足原子性的读命令流程图。也参看图2,分配器从主机接收到来自主机的原子读命令,依据原子读命令所访问的逻辑地址,将读命令分配给用于处理缓存任务的cpu之一(例如,参看图3,cpu0)(也参看图20,步骤2010)。cpu0依据访问的逻辑地址范围,将原子读命令拆分为多个子命令。每次获取属于一原子读命令的未被处理的多个子命令中排序在最前的子命令进行处理(参看图20,步骤2020)。若获取的子命令并非排序在最前的子命令,暂停对该子命令的处理,例如,将其加入等待队列。接下来,cpu0检查要处理的子命令的逻辑地址范围是否超出了自己所管理的逻辑地址范围(参看图20,步骤2030)。若子命令的逻辑地址范围完全落入自身所管理的逻辑地址范围,cpu0在dram中为子命令分配缓存单元,为所分配的缓存单元加锁(参看图20,步骤2040)。响应于加锁成功,若子命令命中了缓存单元,将缓存单元中同子命令对应的数据提供给主机(参看图20,步骤2050);若子命令未命中缓存单元,从nvm芯片中获取子命令所请求的数据,并将数据提供给主机,可选地,还将从nvm芯片中获取的数据存储在缓存单元中。若子命令逻辑地址范围超越了cpu0自身所管理的逻辑地址范围,cpu0向其他cpu(例如,cpu1)请求临时管理写命令所需的逻辑地址范围(参看图20,步骤2032)。在从cpu1获得了缓存单元后,cpu0将该缓存单元分配给子命令,为所分配的缓存单元加锁(参看图20,步骤2040)。响应于加锁成功,若子命令命中了缓存单元,将缓存单元中同子命令对应的数据提供给主机(参看图20,步骤2050);若子命令未命中缓存单元,从nvm芯片中获取子命令所请求的数据,并将数据提供给主机,可选地,还将从nvm芯片中获取的数据存储在缓存单元中。接下来,判断是否已为该原子读命令的所有子命令对应的缓存单元全部加锁(参看图20,步骤2060)。若未全部加锁,获取属于一原子读命令的未被处理的多个子命令的逻辑地址的排序最前的下一子命令并处理该下一个子命令(参看图20,步骤2020)。若为该原子读命令的所有子命令都分配了缓存单元且对应的缓存单元已被全部加锁,响应于所有子命令所对应的数据都被提供给主机,向主机指示该原子读命令处理完成(参看图20,步骤2080),以及释放分配给该原子读命令的所有缓存单元的锁(参看图20,步骤2070),从而这些缓存单元可被分配给其他读命令或写命令。以及对于从其他cpu借用的缓存单元,在缓存单元的锁被释放后,cpu0向其他cpu归还所借用的缓存单元。在根据本申请图20的实施例中,处理每一个原子读命令时,需满足两个条件:(1)按原子读命令的多个子命令的逻辑地址的值的顺序,为每个子命令申请缓存单元,并对缓存单元加锁,仅在加锁成功后,才处理按逻辑地址的值排序的下一子命令;(2)在依据原子读命令的所有子命令都获得了访问数据并发送给主机后,才释放为该原子读命令申请的所有缓存单元的锁。可选地,为对原子读命令的多个子命令按逻辑地址顺序排序,可以按逻辑地址数值的升序排序,也可以按逻辑地址数值的降序排序。无论采用哪种方式作为排序的依据,对于处理的多个原子读命令和/或原子写命令,使用相同的排序方式。在根据本申请的实施例中,在满足上述两个条件的情况下,可以对多个原子读命令的多个子命令并行处理。可选地,若原子读命令指示要访问的物理地址,将根据图20的实施例中对逻辑地址的操作相应替换为物理地址。实施例十五图21是根据本申请实施例的处理原子命令的流程图。根据本申请的实施例,固态存储设备从主机接收io命令,io命令中指示了io命令的类型(例如,读命令或写命令),确定io命令的类型为读命令或写命令(参看图21,步骤2110)。若命令的类型为读命令,还确定该读命令是否需要满足一般原子性(参看图21,步骤2120)。在一个例子中,若该读命令需要满足一般原子性,则按照图20所示的流程来处理该读命令(参看图20)(也参看图21,步骤2124)。若该读命令不需要满足一般原子性,则直接处理属于该读命令的每个子命令(也参看图21,步骤2122)。例如,按照图9所示的流程来处理该读命令(参看图9)。在步骤2110,若命令的类型为写命令,继续确定该写命令是否需要满足一般原子性或掉电原子性(参看图21,步骤2130)。若该写命令需要满足一般原子性或掉电原子性,则按照图11或图12所示的流程该写命令(参看图11或图12)(也参看图21,步骤2134)。若该写命令不需要满足一般原子性或掉电原子性,则直接处理属于该写命令的每个子命令(也参看图21,步骤2132)。例如,按照图7或图8所示的流程来处理该写命令。而若固态存储设备仅需要满足掉电原子性,对于写命令,按图11或图12所示的流程进行处理,而对读命令的处理则无约束(无须为对个子命令按逻辑地址的顺序请求锁)。直接处理属于该读命令的每个子命令。可选地,例如,按照图9所示的流程来处理该读命令(参看图9)。可选地,若原子命令指示要访问的物理地址,将根据图21的实施例中对逻辑地址的操作相应替换为物理地址。实施例十六图22是根据本申请实施例的原子命令的示意图。图23、图24与图25是处理图22的原子命令过程中的缓存单元的示意图。参看图22,固态存储设备从主机接收的原子写命令f、原子读命令g与原子写命令h。原子写命令f被拆分为3个子命令(x(t1),x+1(t2)与x+2(t3)),原子读命令g被分为3个子命令(x(t4),x+1(t8)与x+2(t9)),原子写命令h被分为3个子命令(x(t5)、x+1(t6)与x+2(t7))。t1时刻,获取了原子写命令f的子命令x(t1)。按逻辑地址顺序处理原子写命令f的多个子命令。由于子命令x(t1)是原子写命令f的尚未被处理的多个子命令中逻辑地址排序最前的子命令,可以对子命令x(t1)进行处理。根据逻辑地址x申请到缓存单元2310,对缓存单元2310加锁(参看图23)。图23中,缓存单元2310对应的锁f(t1)指示该缓存单元的锁属于原子写命令f,还在缓存单元2310的元数据中记录其逻辑地址为x。t2时刻,获取了原子写命令f的子命令x+1(t2)。由于子命令x+1(t2)是原子写命令f的尚未被处理的多个子命令中逻辑地址排序最前的子命令,可以对子命令x+1(t2)进行处理。根据逻辑地址x+1申请缓存单元2312,并对缓存单元2312加锁(参看图23)。图23中,缓存单元2312对应的锁f(t2)指示该缓存单元的锁属于原子写命令f,还在缓存单元2312的元数据中记录其逻辑地址为x+1。t3时刻,获取了原子写命令f的子命令x+2(t3)。由于子命令x+2(t3)是原子写命令f的最后一个尚未被处理的子命令,可以对子命令x+2(t3)进行处理。根据逻辑地址x+2申请缓存单元2314,并对缓存单元2314加锁(参看图23)。图23中,缓存单元2314对应的锁f(t3)指示该缓存单元的锁属于原子写命令f,还在缓存单元2314的元数据中记录其逻辑地址为x+2。至此,为原子写命令f的所有子命令都申请了缓存单元,并对缓存单元都加锁成功。在对原子写命令f的所有子命令所对应的数据都被写入各个缓存单元后,向主机指示该原子写命令f处理完成,释放分配给该原子写命令f的所有缓存单元的锁,从而这些缓存单元可被分配给其他写命令。t4时刻,获取了原子读命令g的子命令x(t4)。按逻辑地址顺序处理原子读命令g的多个子命令。由于子命令x(t4)是原子读命令g的尚未被处理的多个子命令中逻辑地址排序最前的子命令,可以对子命令x(t4)进行处理。根据逻辑地址x申请缓存单元2310,并对缓存单元2310加锁(参看图24)(也参看图20,步骤2040)。由于子命令x(t4)命中了缓存单元2310,依据子命令访问的逻辑地址范围将缓存单元2310缓存的数据发送给主机(也参看图20,步骤2050),减少了从nvm芯片获取数据的开销。图24中,缓存单元2310对应的锁g(t4)指示该缓存单元的锁属于原子读命令g。t5时刻,获取了原子写命令h的子命令x(t5)。按逻辑地址顺序处理原子写命令h的多个子命令。由于子命令x(t5)是原子写命令h的尚未被处理的多个子命令中逻辑地址排序最前的子命令,可以对子命令x(t5)进行处理。根据逻辑地址x申请到缓存单元2310,但对缓存单元2310加锁失败,因而暂停对子命令x(t5)的处理。t6时刻,获取了原子写命令h的子命令x+1(t6)。按逻辑地址顺序处理原子写命令h的多个子命令。由于子命令x+1(t6)并非原子写命令h的尚未被处理的多个子命令中逻辑地址排序最前的子命令(子命令x(t5)尚未处理),暂停对子命令x+1(t6)的处理。t7时刻,获取了原子写命令h的子命令x+2(t7)。按逻辑地址顺序处理原子写命令h的多个子命令。由于子命令x+2(t7)不是原子写命令h的尚未被处理的多个子命令中逻辑地址排序最前的子命令,暂停对子命令x+2(t7)的处理。t8时刻,获取了原子读命令g的子命令x+1(t8)。由于子命令x+1(t8)是原子写读令g的尚未被处理的多个子命令中逻辑地址排序最前的子命令,可以对子命令x+1(t8)进行处理。根据逻辑地址x+1申请缓存单元2312,并对缓存单元2312加锁(参看图24)(也参看图20,步骤2040)。由于子命令x+1(t8)命中了缓存单元2312,依据子命令访问的逻辑地址范围将缓存单元2312缓存的数据发送给主机(也参看图20,步骤2050)。图24中,缓存单元2312对应的锁g(t8)指示该缓存单元的锁属于原子读命令g。t9时刻,获取了原子读命令g的子命令x+2(t9)。由于子命令x+2(t9)是原子读命令g的尚未被处理的最后一个的子命令,可以对子命令x+2(t9)进行处理。根据逻辑地址x+2申请缓存单元2314,并对缓存单元2314加锁(参看图24)(也参看图20,步骤2040)。由于子命令x+2(t9)命中了缓存单元2314,依据子命令访问的逻辑地址范围将缓存单元2314缓存的数据发送给主机(也参看图20,步骤2050)。图24中,缓存单元2314对应的锁g(t9)指示该缓存单元的锁属于原子读命令g。至此,为原子读命令g的所有子命令都申请了缓存单元,并对缓存单元都加锁成功(也参看图20,步骤2060)。在根据原子读命令g的所有子命令将所对应的数据提供给主机后,向主机指示该原子读命令g处理完成,释放分配给该原子读命令g的所有缓存单元的锁(也参看图20,步骤2070),从而这些缓存单元可被分配给其他命令。接下来,从等待队列中获取待处理的子命令x(t5),由于子命令x(t5)是原子写命令h的尚未被处理的多个子命令中逻辑地址排序最前的子命令,可以对子命令x(t5)进行处理。根据逻辑地址x申请到缓存单元2310,此时对缓存单元2310加锁成功(参看图25)。图25中,缓存单元2310对应的锁h(t5)指示该缓存单元的锁属于原子写命令h,还在缓存单元2310的元数据中记录其逻辑地址为x。以及从等待队列中获取待处理的子命令x+1(t6),由于子命令x+1(t6)是原子写命令h的尚未被处理的多个子命令中逻辑地址排序最前的子命令,可以对子命令x+1(t6)进行处理。根据逻辑地址x+1申请到缓存单元2312,对缓存单元2312加锁成功(参看图25)。图25中,缓存单元2312对应的锁h(t6)指示该缓存单元的锁属于原子写命令h。从等待队列中获取待处理的子命令x+2(t7),由于子命令x+2(t7)是原子写命令h的尚未被处理的多个子命令中逻辑地址排序最前的子命令,可以对子命令x+2(t7)进行处理。根据逻辑地址x+2申请到缓存单元2314,对缓存单元2312加锁成功(参看图25)。图25中,缓存单元2314对应的锁h(t7)指示该缓存单元的锁属于原子写命令h。至此,为原子写命令h的所有子命令都申请了缓存单元,并对缓存单元都加锁成功。在对原子写命令h的所有子命令所对应的数据都被写入各个缓存单元后,向主机指示该原子写命令h处理完成,释放分配给该原子写命令h的所有缓存单元的锁,从而这些缓存单元可被分配给其他写命令。参看表4,表4的第二行示出了原子写命令f执行完成后的有效结果:在逻辑地址lba(x)、lba(x+1)与lba(x+2)中分别是原子写命令f所写入的数据x(t1)(这里用子命令x(t1)指示该子命令所写入的数据),x+1(t2)和x+2(t3)。图22的三个原子命令中,原子读命令g先于原子写命令h被执行完成。表4的第三行示出了原子读命令g所读到的结果,即从逻辑地址lba(x)、lba(x+1)与lba(x+2)中分别读出原子写命令f所写入的数据x(t1),x+1(t2)和x+2(t3)。表4的第四行示出了原子写命令h执行完成后的有效结果:在逻辑地址lba(x)、lba(x+1)与lba(x+2)中分别是原子写命令h所写入的数据x(t5),x+1(t6)和x+2(t7)。表4实施例十七图26是根据本申请又一实施例的原子命令的示意图。图27、图28与图29是处理图26的原子命令过程中的缓存单元的示意图。参看图26,固态存储设备从主机接收的原子写命令i、原子读命令j与原子写命令k。原子写命令i被拆分为3个子命令(x(t1),x+1(t2)与x+2(t3)),原子读命令j被分为3个子命令(x(t9),x+1(t4)与x+2(t7)),原子写命令k被分为3个子命令(x(t5)、x+1(t6)与x+2(t8))。t1时刻,获取了原子写命令i的子命令x(t1)。按逻辑地址顺序处理原子写命令i的多个子命令。由于子命令x(t1)是原子写命令i的尚未被处理的多个子命令中逻辑地址排序最前的子命令,可以对子命令x(t1)进行处理。根据逻辑地址x申请到缓存单元2710,对缓存单元2710加锁(参看图27)。图27中,缓存单元2710对应的锁i(t1)指示该缓存单元的锁属于原子写命令i,还在缓存单元2710的元数据中记录其逻辑地址为x。t2时刻,获取了原子写命令i的子命令x+1(t2)。由于子命令x+1(t2)是原子写命令i的尚未被处理的多个子命令中逻辑地址排序最前的子命令,可以对子命令x+1(t2)进行处理。根据逻辑地址x+1申请缓存单元2712,并对缓存单元2712加锁(参看图27)。图27中,缓存单元2712对应的锁i(t2)指示该缓存单元的锁属于原子写命令i,还在缓存单元2712的元数据中记录其逻辑地址为x+1。t3时刻,获取了原子写命令i的子命令x+2(t3)。由于子命令x+2(t3)是原子写命令i的尚未被处理的最后一个子命令,可以对子命令x+2(t3)进行处理。根据逻辑地址x+2申请缓存单元2714,并对缓存单元2714加锁(参看图27)。图27中,缓存单元2714对应的锁i(t3)指示该缓存单元的锁属于原子写命令i,还在缓存单元2714的元数据中记录其逻辑地址为x+2。至此,为原子写命令i的所有子命令都申请了缓存单元,并对缓存单元都加锁成功。在对原子写命令i的所有子命令所对应的数据都被写入各个缓存单元后,向主机指示该原子写命令i处理完成,释放分配给该原子写命令i的所有缓存单元的锁,从而这些缓存单元可被分配给其他命令。t4时刻,获取了原子读命令j的子命令x+1(t4)。按逻辑地址顺序处理原子读命令j的多个子命令。由于子命令x+1(t4)不是原子读命令j的尚未被处理的多个子命令中逻辑地址排序最前的子命令,暂停对子命令x+1(t4)的处理。t5时刻,获取了原子写命令k的子命令x(t5)。由于子命令x(t5)是原子写命令k的尚未被处理的多个子命令中逻辑地址排序最前的子命令,可以对子命令x(t5)进行处理。根据逻辑地址x申请到缓存单元2710,并对缓存单元2710加锁(参看图28)。图28中,缓存单元2710对应的锁k(t5)指示该缓存单元的锁属于原子写命令k,还在缓存单元2710的元数据中记录其逻辑地址为x。t6时刻,获取了原子写命令k的子命令x+1(t6)。由于子命令x+1(t6)是原子写命令k的尚未被处理的多个子命令中逻辑地址排序最前的子命令,可以对子命令x+1(t6)进行处理。根据逻辑地址x+1申请到缓存单元2712,并对缓存单元2712加锁(参看图28)。图28中,缓存单元2712对应的锁k(t6)指示该缓存单元的锁属于原子写命令k,还在缓存单元2712的元数据中记录其逻辑地址为x+1。t7时刻,获取了原子读命令j的子命令x+2(t7)。由于子命令x+2(t7)不是原子读命令j的尚未被处理的多个子命令中逻辑地址排序最前的子命令,暂停对子命令x+2(t7)的处理。t8时刻,获取了原子写命令k的子命令x+2(t8)。由于子命令x+2(t8)是原子写命令k的尚未被处理的最后一个的子命令,可以对子命令x+2(t8)进行处理。根据逻辑地址x+2申请到缓存单元2714,并对缓存单元2714加锁(参看图28)。图28中,缓存单元2714对应的锁k(t7)指示该缓存单元的锁属于原子写命令k,还在缓存单元2714的元数据中记录其逻辑地址为x+2。至此,为原子写命令k的所有子命令都申请了缓存单元,并对缓存单元都加锁成功。在对原子写命令k的所有子命令所对应的数据都被写入各个缓存单元后,向主机指示该原子写命令k处理完成,释放分配给该原子写命令k的所有缓存单元的锁,从而这些缓存单元可被分配给其他命令。t9时刻,获取了原子读命令j的子命令x(t9)。按逻辑地址顺序处理原子读命令j的多个子命令。由于子命令x(t9)是原子读命令j的尚未被处理的多个子命令中逻辑地址排序最前的子命令,可以对子命令x(t9)进行处理。根据逻辑地址x申请缓存单元2710,并对缓存单元2710加锁(参看图29)。由于子命令x(t9)命中了缓存单元2710,依据子命令访问的逻辑地址范围将缓存单元2710缓存的数据发送给主机(也参看图20,步骤2050)。图29中,缓存单元2710对应的锁j(t9)指示该缓存单元的锁属于原子读命令j。接下来,从等待队列中获取待处理的子命令x+1(t4)。由于子命令x+1(t4)是原子读命令j的尚未被处理的多个子命令中逻辑地址排序最前的子命令,可以对子命令x+1(t4)进行处理。根据逻辑地址x+1申请到缓存单元2712,此时对缓存单元2712加锁成功(参看图29)(也参看图20,步骤2040)。由于子命令x+1(t4)命中了缓存单元2712,依据子命令访问的逻辑地址范围将缓存单元2712缓存的数据发送给主机(也参看图20,步骤2050)。图29中,缓存单元2712对应的锁j(t4)指示该缓存单元的锁属于原子读命令j。从等待队列中获取待处理的子命令x+2(t7)。由于子命令x+2(t7)是原子写命令j的尚未被处理的最后一个子命令,可以对子命令x+2(t7)进行处理。根据逻辑地址x+2申请到缓存单元2714,对缓存单元2714加锁成功(参看图29)(也参看图20,步骤2040)。由于子命令x+2(t7)命中了缓存单元2714,依据子命令访问的逻辑地址范围将缓存单元2714缓存的数据发送给主机(也参看图20,步骤2050)。图29中,缓存单元2714对应的锁j(t7)指示该缓存单元的锁属于原子读命令j。至此,为原子读命令j的所有子命令都申请了缓存单元,并对缓存单元都加锁成功(也参看图20,步骤2060)。在根据原子读命令j的所有子命令将所对应的数据提供给主机后,向主机指示该原子读命令j处理完成,释放分配给该原子读命令j的所有缓存单元的锁(也参看图20,步骤2070),从而这些缓存单元可被分配给其他命令。参看表5,表5的第二行示出了原子写命令i执行完成后的有效结果:在逻辑地址lba(x)、lba(x+1)与lba(x+2)中分别是原子写命令i所写入的数据x(t1)、x+1(t2)和x+2(t3)。表5的第三行示出了原子写命令k执行完成后的有效结果:在逻辑地址lba(x+1)、lba(x+2)与lba(x+3)中分别是原子写命令k所写入的数据x(t5)、x+1(t6)和x+2(t8)。图26的三个原子命令中,原子写命令k在原子读命令j之前被执行完成。表5的第四行示出了原子读命令j执行完成后的有效结果,即从从逻辑地址lba(x)、lba(x+1)与lba(x+2)中分别读出原子写命令k所写入的数据x(t5),x+1(t6)和x+2(t8)。表5实施例十八图30是根据本申请又一实施例的原子命令的示意图。图31、图32、图33与图33分别是处理图30的原子命令过程中的缓存单元的示意图。参看图30,固态存储设备从主机接收的原子写命令l、原子读命令m、原子写命令n与原子读命令o。原子写命令l被拆分为3个子命令(x(t1),x+1(t6)与x+2(t7)),原子读命令m被分为3个子命令(x(t8),x+1(t9)与x+2(t10)),原子写命令n被分为3个子命令(x+1(t2)、x+2(t4)与x+3(t5)),原子读命令o被分为5个子命令(x-1(t3),x(t11),x+1(t12),x+2(t13)与x+3(t14))。t1时刻,获取了原子写命令l的子命令x(t1)。按逻辑地址顺序处理原子写命令l的多个子命令。由于子命令x(t1)是原子写命令l的尚未被处理的多个子命令中逻辑地址排序最前的子命令,可以对子命令x(t1)进行处理。根据逻辑地址x申请到缓存单元3110,对缓存单元3110加锁(参看图31)。图31中,缓存单元3110对应的锁l(t1)指示该缓存单元的锁属于原子写命令l,还在缓存单元3110的元数据中记录其逻辑地址为x。t2时刻,获取了原子写命令n的子命令x+1(t2)。按逻辑地址顺序处理原子写命令n的多个子命令。由于子命令x+1(t2)是原子写命令n的尚未被处理的多个子命令中逻辑地址排序最前的子命令,可以对子命令x+1(t2)进行处理。根据逻辑地址x+1申请缓存单元3112,并对缓存单元3112加锁(参看图31)。图31中,缓存单元3112对应的锁n(t2)指示该缓存单元的锁属于原子写命令n,还在缓存单元3112的元数据中记录其逻辑地址为x+1。t3时刻,获取了原子读命令o的子命令x-1(t3)。按逻辑地址顺序处理原子读命令o的多个子命令。由于子命令x-1(t3)是原子读命令o的尚未被处理的多个子命令中逻辑地址排序最前的子命令,可以对子命令x-1(t3)进行处理。根据逻辑地址x-1申请缓存单元3118,并对缓存单元3118加锁(参看图31)。图31中,缓存单元3118对应的锁o(t3)指示该缓存单元的锁属于原子读命令o,还在缓存单元3118的元数据中记录其逻辑地址为x-1。t4时刻,获取了原子写命令n的子命令x+2(t4)。由于子命令x+2(t4)是原子写命令n的尚未被处理的多个子命令中逻辑地址排序最前的子命令,可以对子命令x+2(t4)进行处理。根据逻辑地址x+2申请缓存单元3114,并对缓存单元3114加锁(参看图31)。图31中,缓存单元3114对应的锁n(t4)指示该缓存单元的锁属于原子写命令n,还在缓存单元3114的元数据中记录其逻辑地址为x+2。t5时刻,获取了原子写命令n的子命令x+3(t5)。由于子命令x+3(t5)是原子写命令n的尚未被处理的多个子命令中逻辑地址排序最前的子命令,可以对子命令x+3(t5)进行处理。根据逻辑地址x+3申请缓存单元3116,并对缓存单元3116加锁(参看图31)。图31中,缓存单元3116对应的锁n(t5)指示该缓存单元的锁属于原子写命令n,还在缓存单元3116的元数据中记录其逻辑地址为x+3。至此,为原子写命令n的所有子命令都申请了缓存单元,并对缓存单元都加锁成功。在对原子写命令n的所有子命令所对应的数据都被写入各个缓存单元后,向主机指示该原子写命令n处理完成,释放分配给该原子写命令n的所有缓存单元的锁,从而这些缓存单元可被分配给其他命令。t6时刻,获取了原子写命令l的子命令x+1(t6)。由于子命令x+1(t6)是原子写命令l的尚未被处理的多个子命令中逻辑地址排序最前的子命令,可以对子命令x+1(t6)进行处理。根据逻辑地址x+1申请缓存单元3112,并对缓存单元3112加锁(参看图32)。图32中,缓存单元3112对应的锁l(t6)指示该缓存单元的锁属于原子写命令l,还在缓存单元3112的元数据中记录其逻辑地址为x+1。t7时刻,获取了原子写命令l的子命令x+2(t7)。由于子命令x+2(t7)是原子写命令l的尚未被处理的多个子命令中逻辑地址排序最前的子命令,可以对子命令x+2(t7)进行处理。根据逻辑地址x+2申请缓存单元3114,并对缓存单元3114加锁(参看图32)。图32中,缓存单元3114对应的锁l(t7)指示该缓存单元的锁属于原子写命令l,还在缓存单元3114的元数据中记录其逻辑地址为x+2。至此,为原子写命令l的所有子命令都申请了缓存单元,并对缓存单元都加锁成功。在对原子写命令l的所有子命令所对应的数据都被写入各个缓存单元后,向主机指示该原子写命令l处理完成,释放分配给该原子写命令l的所有缓存单元的锁,从而这些缓存单元可被分配给其他命令。t8时刻,获取了原子读命令m的子命令x(t8)。按逻辑地址顺序处理原子读命令m的多个子命令。由于子命令x(t8)是原子读命令m的尚未被处理的多个子命令中逻辑地址排序最前的子命令,可以对子命令x(t8)进行处理。根据逻辑地址x申请缓存单元3110,并对缓存单元3110加锁(参看图33)。由于子命令x(t8)命中了缓存单元3110,依据子命令访问的逻辑地址范围将缓存单元3110缓存的数据发送给主机。图33中,缓存单元3110对应的锁m(t8)指示该缓存单元的锁属于原子读命令m。t9时刻,获取了原子读命令m的子命令x+1(t9)。由于子命令x+1(t9)是原子读命令m的尚未被处理的多个子命令中逻辑地址排序最前的子命令,可以对子命令x+1(t9)进行处理。根据逻辑地址x+1申请缓存单元3112,并对缓存单元3112加锁(参看图33)。由于子命令x+1(t9)命中了缓存单元3112,依据子命令访问的逻辑地址范围将缓存单元3112缓存的数据发送给主机。图33中,缓存单元3112对应的锁m(t9)指示该缓存单元的锁属于原子读命令m。t10时刻,获取了原子读命令m的子命令x+2(t10)。由于子命令x+2(t10)是原子读命令m的尚未被处理的多个子命令中逻辑地址排序最前的子命令,可以对子命令x+2(t10)进行处理。根据逻辑地址x+2申请缓存单元3114,并对缓存单元3114加锁(参看图33)。由于子命令x+2(t10)命中了缓存单元3114,依据子命令访问的逻辑地址范围将缓存单元3114缓存的数据发送给主机。图33中,缓存单元3114对应的锁m(t10)指示该缓存单元的锁属于原子读命令m。至此,为原子读命令m的所有子命令都申请了缓存单元,并对缓存单元都加锁成功(也参看图20,步骤2060)。在根据原子读命令m的所有子命令将所对应的数据提供给主机后,向主机指示该原子读命令m处理完成,释放分配给该原子读命令m的所有缓存单元的锁(也参看图20,步骤2070),从而这些缓存单元可被分配给其他命令。t11时刻,获取了原子读命令o的子命令x(t11)。由于子命令x(t11)是原子读命令o的尚未被处理的多个子命令中逻辑地址排序最前的子命令,可以对子命令x(t11)进行处理。根据逻辑地址x申请缓存单元3110,并对缓存单元3110加锁(参看图34))。由于子命令x(t11)命中了缓存单元3110,依据子命令访问的逻辑地址范围将缓存单元3110缓存的数据发送给主机。图34中,缓存单元3110对应的锁o(t11)指示该缓存单元的锁属于原子读命令o。t12时刻,获取了原子读命令o的子命令x+1(t12)。由于子命令x(t11)是原子读命令o的尚未被处理的多个子命令中逻辑地址排序最前的子命令,可以对子命令x+1(t12)进行处理。根据逻辑地址x+1申请缓存单元3112,并对缓存单元3112加锁(参看图34)。由于子命令x+1(t12)命中了缓存单元3112,依据子命令访问的逻辑地址范围将缓存单元3112缓存的数据发送给主机。图34中,缓存单元3112对应的锁o(t12)指示该缓存单元的锁属于原子读命令o。t13时刻,获取了原子读命令o的子命令x+2(t13)。由于子命令x+2(t13)是原子读命令o的尚未被处理的多个子命令中逻辑地址排序最前的子命令,可以对子命令x+2(t13)进行处理。根据逻辑地址x+2申请缓存单元3114,并对缓存单元3114加锁(参看图34)。由于子命令x+2(t13)命中了缓存单元3114,依据子命令访问的逻辑地址范围将缓存单元3114缓存的数据发送给主机。图34中,缓存单元3114对应的锁o(t13)指示该缓存单元的锁属于原子读命令o。t14时刻,获取了原子读命令o的子命令x+3(t14)。由于子命令x+3(t14)是原子读命令o的尚未被处理的多个子命令中逻辑地址排序最前的子命令,可以对子命令x+3(t14)进行处理。根据逻辑地址x+3申请缓存单元3116,并对缓存单元3116加锁(参看图34)。由于子命令x+3(t14)命中了缓存单元3114,依据子命令访问的逻辑地址范围将缓存单元3116缓存的数据发送给主机。图34中,缓存单元3116对应的锁o(t14)指示该缓存单元的锁属于原子读命令o。至此,为原子读命令o的所有子命令都申请了缓存单元,并对缓存单元都加锁成功(也参看图20,步骤2060)。在根据原子读命令o的所有子命令将所对应的数据提供给主机后,向主机指示该原子读命令o处理完成,释放分配给该原子读命令o的所有缓存单元的锁(也参看图20,步骤2070),从而这些缓存单元可被分配给其他命令。如上所述,图30中的四条原子命令,按原子写命令n、原子写命令l、原子读命令m以及原子读命令o的顺序被处理完成。参看表6,表6的第二行示出了原子写命令n执行完成后的有效结果:在lba(x+1)、lba(x+2)与lba(x+3)中分别是原子写命令n所写入的数据x+1(t2)、x+2(t4)和x+3(t5)。表6的第三行示出了原子写命令l执行完成后的有效结果:在lba(x)、lba(x+1)与lba(x+2)中分别是原子写命令l所写入的数据x(t1)、x+1(t6)、x+2(t7),以及在lba(x+3)中是原子写命令n所写入的数据x+3(t5)。图30的四个原子命令中,原子写命令n与原子写命令l在原子读命令m与原子读命令o之前被依次执行完成。表6的第四行示出了原子读命令m执行完成后所读到的结果,即从从逻辑地址lba(x)、lba(x+1)与lba(x+2)中分别读出原子写命l所写入的数据x(t1),x+1(t6)和x+2(t7)。表6的第五行示出了原子读命令o执行完成后所读到的结果。表6以上所述,仅为本申请的具体实施方式,但本申请的保护范围并不局限于此,任何熟悉本
技术领域
的技术人员在本申请揭露的技术范围内,可轻易想到变化或替换,都应涵盖在本申请的保护范围之内。因此,本申请的保护范围应以权利要求的保护范围为准。当前第1页12
当前第1页1 2 
网友询问留言 已有0条留言
  • 还没有人留言评论。精彩留言会获得点赞!
1