大家好我是小义同学,这是大厂面试拆解——项目实战系列的第5篇文章,
”走暗路、耕瘦田、进窄门、见微光” 告诉我 面试关键就 深入理解自己项目 这个才是最考察基本功的地方。
知识地图:KV存储引擎---BlueStore
Ceph分布式锁的设计哲学与工程实践 提到 为了支持海量并发,满足多客户端,主副本等多节点数据达成一致, 设计了分布式锁,分布式锁特点
本文 主要介绍什么是BlueStore,如何快速理解BlueStore并且进行优化。
Ceph 12.2.0 正式版本发布
BlueStore 是一个从头开始设计的存储后端, 旨在解决使用本地文件系统后端所面临的挑战。
BlueStore 仅用两年时间就实现了所有这些目标, 并成为 Ceph 的默认存储后端
文件系统作为分布式存储后端:从 Ceph 十年进化中汲 取的教训
上图看出 ceph不停变换后端从FileStore到BlueStore
BlueStore 的一些主要目标包括:
对比如下:
BlueStore vs FileStore | FileStore (基于文件系统) | BlueStore (直接管理裸设备) | 核心优势说明 |
---|---|---|---|
系统架构 | XFS + LevelDB | RocksDB + 块设备 | 绕过文件系统直接管理磁盘,降低软件栈复杂度 |
双写问题 | 存在 | 无(原子写操作) | 消除写放大,提升性能 |
批量读取 | 通过 XFS 文件系统读取(百万级别) | RocksDB 元数据 + 直接块设备访问 | 减少 I/O 路径延迟 |
对象列举 | 需对 XFS 文件排序 | RocksDB 预排序键值(LSM 树结构**) | 列表操作快 10 倍以上 |
批量删除 | 逐个删除 XFS 文件 | 批量删除 RocksDB 键值,批量事务 | 删除速度提升 50-100 倍 |
对象读缓存 | 依赖 XFS 缓存机制 | 需用户态实现(如 LRU 缓存) | 灵活性更高,可定制化 |
# Crimson: Next-generation Ceph OSD for Multi-core Scalability
Crimson 是基于 Seastar C++ 框架实现的 Ceph 下一代 OSD,用以提升多核可扩展性与 I/O 性能。
Crimson 被设计为高性能对象存储守护程序 (OSD),针对 NVMe 等快速存储设备进行了优化。
为了实现这些目标,Crimson 使用包括 SPDK、DPDK 和 C++ Seastar 框架在内的尖端技术从头开始构建。
Crimson 继续沿用 BlueStore 作为底层存储后端
并在未来计划通过原生 Seastore 存储后端摆脱对 BlueStore 的依赖
架构如下:
BlueStore主要4个技术点:
聪明你可能你会疑问:
聪明你可能你会疑问 : 为了使用RocksDB,有写一个文件系统?
BlueStore是基于RocksDB和BlockDevice实现的ceph的对象存储
目的:假设你需要对BlueStore优化,必须了解 IO过程是什么
fio -name=iouring_test
-filename=/mnt/vdd/testfile
-iodepth=32 //I/O 引擎若使用异步模式,保持队列深度
-thread
-rw=randread
//定义 IO 类型。
//随机读 randread、
//随机写 randwrite、顺序读 read、顺序写 write、顺序读写
//rw readwrite ,随机混合读写 randrw
-ioengine=io_uring //IO 引擎。同步模式psync、异步模式io_uring
-sqthread_poll=1
-direct=1
//是否使用 direct io,测试过程不使用OS 自带的buffer,使测试磁盘的结果更真实
//direct io,跳过缓存,直接读写SSD
-bs=4k //IO 的块大小。默认 4k
-size=10G
-numjobs=1 //thread number
-runtime=120 告诉fio在指定的时间段后终止处理。
-group_reporting
测试结果:
推荐的基准测试工具
1. fio -ioengine=rbd -direct=1 -name=test -bs=4M -iodepth=16 -rw=write -pool=rpool_hdd -runtime=60 -rbdname=testimg
2. fio -ioengine=rbd -direct=1 -name=test -bs=4k -iodepth=1 -rw=randwrite -pool=rpool_hdd -runtime=60 -rbdname=testimg
3. fio -ioengine=rbd -direct=1 -name=test -bs=4k -iodepth=128 -rw=randwrite -pool=rpool_hdd -runtime=60 -rbdname=testimg
测试方法1 绕过文件系统,读NVMe_ ssd进行fio的读盘操作 iops 10w-80w
针对测试CEPH集群的性能时,nvme ssd的读写iops总量不超过4w+ why?
首先的青铜猜想是:
fio
只是本地落盘,时延极小,因此能将 SSD 压。大师理解的猜想
Ceph OSD 多层软件栈开销
BlueStore
可以理解为一个支持ACID
事物型的 本地日志文件系统。基本流程
const char *get_state_name() {
switch (state) {
case STATE_PREPARE: return "prepare";
//主要工作:
//该阶段主要是IO前的准备工作
//这个阶段会调用`_txc_add_transaction`将OSD层面的事物转换为BlueStore层面的事物
//延迟指标:
//l_bluestore_state_prepare_lat,从进入状态机到prepare阶段完成,
case STATE_AIO_WAIT: return "aio_wait";
//主要工作:
//该阶段等待aio的完成
//aio完成后在回调函数中将事务状态设置为STATE_IO_DONE
//延迟指标:
//l_bluestore_state_aio_wait_lat,从prepare阶段完成开始到AIO完成,
//平均延迟受限于设备,SSD 0.03ms左右。
case STATE_IO_DONE: return "io_done";
//主要工作:
//该阶段完对IO进行保序,保证kv事务的顺序性。
//按顺序设置事务状态为STATE_KV_QUEUED,将事务放入kv_queue
//通知kv_sync_thread进行,去同步IO和元数据
//kv_sync_thread 线程调用 db->submit_transaction 将批量更新写入 RocksDB
//IO保序可能会block。
//延迟指标:
//l_bluestore_state_io_done_lat,
//平均延迟在0.004ms,通常很小主要耗在对SimpleWrite的IO保序处理上。
//下个阶段:STATE_KV_QUEUED阶段
case STATE_KV_QUEUED: return "kv_queued";
//主要工作:
//1 该阶段主要deal kv_sync_thread线程中把aio的元数据写入kv数据库
//2 将状态设置为STATE_KV_SUBMITTED。
//3 然后将事务放入kv_committing_to_finalize队列,并通知_kv_finalize_thread线程处理
//延迟指标:
//l_bluestore_state_kv_queued_lat,
case STATE_KV_COMMITTING: return "kv_committing";
//主要工作:等待kv元数据和IO数据的Sync完成,回调finisher线程
//该阶段主要在 kv_finalize_thread线程中将状态设置为STATE_KV_DONE
//并将回调函数放入finisher队列,在finisher线程中给客户端返回应答
//延迟指标:
//l_bluestore_state_kv_done_lat
case STATE_KV_DONE: return "kv_done";
//主要工作
//如果没有延迟IO,则直接将状态设置为STATE_FINISHING;
//如果有延时IO,则将状态设置为STATE_DEFERRED_QUEUED
case STATE_WAL_QUEUED: return "wal_queued";
case STATE_WAL_APPLYING: return "wal_applying";
case STATE_WAL_AIO_WAIT: return "wal_aio_wait";
case STATE_WAL_CLEANUP: return "wal_cleanup";
case STATE_WAL_DONE: return "wal_done";
case STATE_FINISHING: return "finishing";
case STATE_DONE: return "done";
//延迟统计
enum {
l_bluestore_state_prepare_lat,
l_bluestore_state_aio_wait_lat,
l_bluestore_state_io_done_lat,
l_bluestore_state_kv_queued_lat,
l_bluestore_state_kv_committing_lat,
l_bluestore_state_kv_done_lat,
l_bluestore_state_wal_queued_lat,
l_bluestore_state_wal_applying_lat,
l_bluestore_state_wal_aio_wait_lat,
l_bluestore_state_wal_cleanup_lat,
l_bluestore_state_finishing_lat,
}
BlueStore IO流程
在处理simple-write时, 需要考虑offset、length是否对齐到block_size(4KB)以进行补零对齐的操作。
写k/v日志:
STATE_PREPARE -> STATE_IO_DONE -> STATE_KV_QUEUED -> STATE_KV_SUBMITTED -> STATE_KV_DONE -> STATE_DEFERRED_QUEUE
写数据:
STATE_DEFERRED_QUEUE -> STATE_DEFERRED_CLEANUP -> STATE_FINISHING -> STATE_DONE
慢点集中在哪里?
综合来看,RocksDB 同步提交(阶段4) 和 AIO 等待(阶段2) 是占比最高的两部分, 共计可超过 80% 的
64K随机写入(QD=16场景)
kv_sync_thread
需串行处理元数据提交,导致高QD下队列堆积(如kv_queued_lat
从0.005ms升至0.544msio_submit
在高并发时需频繁上下文切换,占用CPU核心资源原创声明:本文系作者授权腾讯云开发者社区发表,未经许可,不得转载。
如有侵权,请联系 cloudcommunity@tencent.com 删除。
原创声明:本文系作者授权腾讯云开发者社区发表,未经许可,不得转载。
如有侵权,请联系 cloudcommunity@tencent.com 删除。