长治电子商务网站建设,哪个网站能把图片拼凑起来做gif的,建站方法,专升本要什么条件摘自#xff1a;https://mp.weixin.qq.com/s/oWujGOLLGItu1Bv5AuO0-A 2020-09-02 21:45
0.引言 Ceph是国际知名的开源分布式存储系统#xff0c;在工业界和学术界都有着重要的影响。Ceph的架构和算法设计发表在国际系统领域顶级会议OSDI、SOSP、SC等上。Ceph社区得到Red Hat…摘自https://mp.weixin.qq.com/s/oWujGOLLGItu1Bv5AuO0-A 2020-09-02 21:45
0.引言 Ceph是国际知名的开源分布式存储系统在工业界和学术界都有着重要的影响。Ceph的架构和算法设计发表在国际系统领域顶级会议OSDI、SOSP、SC等上。Ceph社区得到Red Hat、SUSE、Intel等大公司的大力支持。Ceph是国际云计算领域应用最广泛的开源分布式存储系统此外Ceph也广泛应用在文件、对象等存储领域。Ceph在滴滴也支撑了很多关键业务的运行。在Ceph的大规模部署和使用过程中我们发现了Ceph的一些性能问题。围绕Ceph的性能优化我们做了很多深入细致的工作。这篇文章主要介绍我们通过调试分析发现的Ceph在锁方面存在的问题和我们的优化方法。
1. 背景 在支撑一些延迟敏感的在线应用过程中我们发现Ceph的尾延迟较差当应用并发负载较高时Ceph很容易出现延迟的毛刺对延迟敏感的应用造成超时甚至崩溃。我们对Ceph的尾延迟问题进行了深入细致的分析和优化。造成尾延迟的一个重要原因就是代码中锁的使用问题下面根据锁问题的类型分别介绍我们的优化工作。本文假设读者已熟悉Ceph的基本读写代码流程代码的版本为Luminous。
2. 持锁时间过长 ▍2.1 异步读优化 Ceph的osd处理客户端请求的线程池为osd_op_tp在处理操作请求的时候线程会先锁住操作对应pg的lock。其中处理对象读请求的代码如下图所示在锁住对象所属pg的lock后对于最常用的多副本存储方式线程会同步进行读操作直到给客户端发送返回的数据后才会释放pg lock。 在进行读操作时如果数据没有命中page cache而需要从磁盘读是一个耗时的操作并且pg lock是一个相对粗粒度的锁在pg lock持有期间其它同属一个pg的对象的读写操作都会在加锁上等待增大了读写延迟降低了吞吐率。同步读的另一个缺点是读操作没有参与流量控制。 我们对线上集群日志的分析也验证了上述问题例如一个日志片段如下图所示图中列举了两个op的详细耗时信息这两个op均为同一个osd的线程所执行且操作的是同一个pg的对象。根据时间顺序第一个op为read总耗时为56ms。第二个op为write总耗时为69ms。图中信息显示第二个op处理的一个中间过程即副本写的完成消息在处理之前在osd请求队列中等待了36ms。结合上图的代码可以知道这36ms都是耗在等待pg lock上因为前一个read操作持有pg lock而两个对象属于相同pg。 我们的优化如下图所示我们创建了独立的读线程负责处理读请求osd_op_tp线程只需将读请求提交到读线程的队列即可返回解锁大大减少了pg lock的持有时间。读线程完成磁盘读之后将结果放到finisher线程的队列finisher线程重新申请pg lock后负责后续处理这样将耗时的磁盘访问放在了不持有pg lock的流程中结合我们在流量控制所做的优化读写操作可以在统一的框架下进行流量控制从而精准控制磁盘的利用率以免磁盘访问拥塞造成尾延迟。 我们用fio进行了异步读优化效果的测试测试方法对同一个pool的两个rbd一个做随机读另一个同时做随机写操作将pg number配置为1这样所有对象读写会落到同一个osd的同一个pg。异步读优化后随机写平均延迟下降了53%。下图为某业务的filestore集群异步读上线前后读吞吐率的数据箭头所指为上线时间可见上线之后集群承载的读操作的吞吐率增加了120%。 上述优化在使用filestore存储后端时取得了明显的效果但在使用bluestore存储后端时bluestore代码中还存在持有pg粒度锁同步读的问题具体见BlueStore::read的代码。我们对bluestore的读也进行了异步的优化这里就不详细介绍了。 3. 锁粒度过粗 ▍3.1 object cache lock优化 Ceph在客户端实现了一个基于内存的object cache供rbd和cephfs使用。但cache只有一把大的互斥锁任何cache中对象的读写都需要先获得这把锁。在使用写回模式时cache flusher线程在写回脏数据之前也会锁住这个锁。这时对cache中缓存对象的读写都会因为获取锁而卡住使读写延迟增加限制了吞吐率。 我们实现了细粒度的对象粒度的锁在进行对象的读写操作时只需获取对应的对象锁无需获取全局锁。只有访问全局数据结构时才需要获取全局锁大大增加了对象间操作的并行。并且对象锁采用读写锁增加了同一对象上读的并行。测试表明高并发下rbd的吞吐率增加了超过20%。
4. 不必要的锁竞争 ▍4.1减少pg lock竞争 Ceph的osd对客户端请求的处理流程为messenger线程收到请求后将请求放入osd_op_tp线程池的缓存队列。osd_op_tp线程池的线程从请求缓存队列中出队一个请求然后根据该请求操作的对象对应的pg将请求放入一个与pg一一对应的pg slot队列的尾部。然后获取该pg的pg lock从pg slot队列首部出队一个元素处理。 可见如果osd_op_tp线程池的请求缓存队列中连续两个请求操作的对象属于相同的pg则一个osd_op_tp线程出队前一个请求加入pg slot队列后获取pg lock从pg slot队列首部出队一个请求开始处理。另一个osd_op_tp线程从请求缓存队列出队第二个请求因为两个请求是对应相同的pg则它会加入相同的pg slot队列然后第二个线程在获取pg lock时会阻塞。这降低了osd_op_tp线程池的吞吐率增加了请求的延迟。 我们的优化方式是保证任意时刻每个pg slot队列只有一个线程处理。因为在处理pg slot队列中的请求之前需要获取pg lock因此同一个pg slot队列的请求是无法并行处理的。我们在每个pg slot队列增加一个标记记录当前正在处理该pg slot的请求的线程。当有线程正在处理一个pg slot的请求时别的线程会跳过处理该pg slot继续从osd_op_tp线程池的请求缓存队列出队请求。
▍4.2 log lock优化 Ceph的日志系统实现是有一个全局的日志缓存队列由一个全局锁保护由专门的日志线程从日志缓存队列中取日志打印。工作线程提交日志时需要获取全局锁。日志线程在获取日志打印之前也需要获取全局锁然后做一个交换将队列中的日志交换到一个临时队列。另外当日志缓存队列长度超过阈值时提交日志的工作线程需要睡眠等待日志线程打印一些日志后再提交。锁的争抢和等待都增加了工作线程的延迟。 我们为每个日志提交线程引入一个线程局部日志缓存队列该队列为经典的单生产者单消费者无锁队列。线程提交日志直接提交到自己的局部日志缓存队列该过程是无锁的。只有队列中的日志数超过阈值后才会通知日志线程。日志线程也会定期轮询各个日志提交线程的局部日志缓存队列打印一些日志该过程也是无锁的。通过上述优化基本避免了日志提交过程中因为锁竞争造成的等待降低了日志的提交延迟。测试在高并发日志提交时日志的提交延迟可降低接近90%。
▍4.3 filestore apply lock优化 对于Ceph filestore存储引擎同一个pg的op需要串行apply。每个pg有一个OpSequencer(简称osr)用于控制apply顺序每个osr有一个apply lock以及一个op队列。对于每个待apply的op首先加入对应pg的osr的队列然后把osr加到filestore的负责apply的线程池op_tp的队列简称为apply队列。op_tp线程从apply队列中取出一个osr加上它的apply lock再从osr的队列里取出一个op apply逻辑代码如下图左所示。可见每个op都会把其对应的osr加入到apply队列一次。如果多个op是针对同一个pg的对象则这个pg的osr可能多次加入到apply队列。如果apply队列中连续两个osr是同一个pg的也就是同一个osr则前一个op被一个线程进行apply时osr的apply lock已经加锁另一个线程会在该osr的apply lock上阻塞等待降低了并发度。 这个问题也体现在日志中。一个线上集群日志片段如下图有两个op_tp线程6700和5700apply队列里三个对象依次来自pg: 1.1833, 1.1833. 1.5f2。线程6700先拿到第一个对象进行apply, 线程5700拿第二个对象进行apply时卡在apply lock上因为两个对象都来自pg 1.1833直到6700做完才开始apply。而6700拿到第三个对象即1.5f2的对象进行apply即写page cache只用了不到1ms但实际apply延迟234ms可见第三个对象在队列里等待了233ms。如果5700不用等待apply lock则第二和第三个对象的apply延迟可以大大缩短。 我们优化后的逻辑代码如上图右所示同一个osr只加入apply队列一次取消apply lock利用原子操作实现无锁算法。上面的算法可以进一步优化在将一个osr出队之后可以一次从它的队列中取m(m1)个op进行apply在op apply完成阶段改为如果atomic::fetch_sub(osr-queue_length, m) m则将osr重新入队以提高吞吐率。 我们用fio进行了apply lock优化效果测试方法为建两个pool每个pool的pg number为1每个pool一个rbd, 对两个rbd同时进行随机写的操作一个pool写入数据的量为31k*10k另一个pool写入数据的量为4k*100k, 衡量所有请求apply的总耗时。优化前总耗时434ks, 优化后总耗时45ks减少89.6%。 团队介绍 滴滴云平台事业群滴滴云存储团队原隶属于滴滴基础平台部现隶属于新成立的滴滴云事业部。团队承担着公司在线非结构化存储服务的研发并参与运维工作。具体来说团队承担了公司内外部业务的绝大部分的对象、块、文件存储需求数据存储量数十PB。团队技术氛围浓厚同时具备良好的用户服务意识立足于用技术创造客户价值业务上追求极致。团队对于分布式存储、互联网服务架构、Linux存储栈有着深入的理解。
作者介绍 负责滴滴在线非结构化存储研发曾任国防科技大学计算机学院副研究员教研室主任天河云存储负责人