在FileStore下,用户文件经过切分对象块后最终存放在了单机文件系统(xfs 、ext4等)中,我们可以较容易地找到这些对象块对应的文件,然后提取这些对象块文件后组装成用户文件。然而,BlueStore是构建在裸盘上的,没有文件之说,我们提取用户文件时就需要知道用户文件的坐落在裸盘的哪些空间(位置+大小:offset + length)上。下面笔者就介绍下笔者是怎么提取BlueStore中的文件的~

一、需要了解的一些概念

如果笔者理解有误,请留言指正~

概念 解释
onode 每个对象有个onode
lextent 逻辑extent
extent_map 存放 lextent 的map
extent_map shard extent map较大时切分shard
blob lextent占据blob的一段或这全部 ,blob内可以有多个lextent
pextent 物理extent,blob由一个或多个 pextent 组成 
pextent 含字段 offset+length,代表裸盘的一段空间

几个概念的关系如图:

此图源于网络(http://www.sysnote.org/2016/08/19/ceph-bluestore/),如有冒犯,请联系笔者删除~

 

二、使用 ceph-kvstore-tool 工具获得用户文件位置

集群中有名为ceph-osd.0.log的文件:

[root@s131 /data]# ls -i /cephfs
1099511627776 ceph-osd.0.log 1099511627777 test

获取该文件的十六进制inode号:

[root@s131 /data]# printf %llx 1099511627776
10000000000

使用 ceph osd map fs_d 10000000000.00000000 命令可以取得该对象所在的osd ${OSDID},通过 ceph-kvstore-tool 工具查看其 onode 和 onode的extent_map的shard:

[root@s131 /data]# ceph-kvstore-tool bluestore-kv  /data/lib/ceph/osd/ceph-${OSDID} list O 2>/dev/null  |grep 10000000000.00000000
O %7f%80%00%00%00%00%00%00%02%0c%f6%ad%0f%2110000000000.00000000%21%3d%ff%ff%ff%ff%ff%ff%ff%fe%ff%ff%ff%ff%ff%ff%ff%ffo
O %7f%80%00%00%00%00%00%00%02%0c%f6%ad%0f%2110000000000.00000000%21%3d%ff%ff%ff%ff%ff%ff%ff%fe%ff%ff%ff%ff%ff%ff%ff%ffo%00%00%00%00x
O %7f%80%00%00%00%00%00%00%02%0c%f6%ad%0f%2110000000000.00000000%21%3d%ff%ff%ff%ff%ff%ff%ff%fe%ff%ff%ff%ff%ff%ff%ff%ffo%00%08%00%00x
O %7f%80%00%00%00%00%00%00%02%0c%f6%ad%0f%2110000000000.00000000%21%3d%ff%ff%ff%ff%ff%ff%ff%fe%ff%ff%ff%ff%ff%ff%ff%ffo%00%10%00%00x
O %7f%80%00%00%00%00%00%00%02%0c%f6%ad%0f%2110000000000.00000000%21%3d%ff%ff%ff%ff%ff%ff%ff%fe%ff%ff%ff%ff%ff%ff%ff%ffo%00%18%00%00x
O %7f%80%00%00%00%00%00%00%02%0c%f6%ad%0f%2110000000000.00000000%21%3d%ff%ff%ff%ff%ff%ff%ff%fe%ff%ff%ff%ff%ff%ff%ff%ffo%00%20%00%00x
O %7f%80%00%00%00%00%00%00%02%0c%f6%ad%0f%2110000000000.00000000%21%3d%ff%ff%ff%ff%ff%ff%ff%fe%ff%ff%ff%ff%ff%ff%ff%ffo%00%28%00%00x
O %7f%80%00%00%00%00%00%00%02%0c%f6%ad%0f%2110000000000.00000000%21%3d%ff%ff%ff%ff%ff%ff%ff%fe%ff%ff%ff%ff%ff%ff%ff%ffo%00%2a%10%00x

第一个kv对象是onode,后面每一个kv对象是onode的extent_map的一个shard
使用 ceph-kvstore-tool 的get命令可以将kv对象保存成文件:

ceph-kvstore-tool  bluestore-kv  /data/lib/ceph/osd/ceph-0 get O %7f%80%00%00%00%00%00%00%02%0c%f6%ad%0f%2110000000000.00000000%21%3d%ff%ff%ff%ff%ff%ff%ff%fe%ff%ff%ff%ff%ff%ff%ff%ffo out onode_out_file

要获取用户的存储位置,就需要获得onode最终存储在哪些pextent上,而这个信息是存储在onode的extent_map中的,我们需要将这些信息加载到内存,然后dump出来

笔者对 ceph-kvstore-tool 进行修改,在get onode时,将onode及其extent_map都加载到内存中,然后dump出来:

_dump_onode 0x7f67c86bf440 #2:0cf6ad0f:::10000000000.00000000:head# nid 151669 size 0x2a1a47 (2759239) expected_object_size 0 expected_write_size 0 in 7 shards, 1 spanning blobs
_dump_onode attr _ len 275
_dump_onode attr snapset len 35
_dump_extent_map shard 0x0(0x211 bytes) (loaded)
_dump_extent_map shard 0x80000(0x213 bytes) (loaded)
_dump_extent_map shard 0x100000(0x213 bytes) (loaded)
_dump_extent_map shard 0x180000(0x213 bytes) (loaded)
_dump_extent_map shard 0x200000(0x213 bytes) (loaded)
_dump_extent_map shard 0x280000(0x97 bytes) (loaded)
_dump_extent_map shard 0x2a1000(0x9 bytes) (loaded)
_dump_extent_map 0x0~80000: 0x0~80000 Blob(0x7f67c87004c0 blob([0x86d626d000~80000] csum crc32c/0x1000) use_tracker(0x80*0x1000 0x[1000,1000,1000,1000,1000,1000,1000,1000,1000,1000,1000,1000,1000,1000,1000,1000,1000,1000,1000,1000,1000,1000,1000,1000,1000,1000,1000,1000,1000,1000,1000,1000,1000,1000,1000,1000,1000,1000,1000,1000,1000,1000,1000,1000,1000,1000,1000,1000,1000,1000,1000,1000,1000,1000,1000,1000,1000,1000,1000,1000,1000,1000,1000,1000,1000,1000,1000,1000,1000,1000,1000,1000,1000,1000,1000,1000,1000,1000,1000,1000,1000,1000,1000,1000,1000,1000,1000,1000,1000,1000,1000,1000,1000,1000,1000,1000,1000,1000,1000,1000,1000,1000,1000,1000,1000,1000,1000,1000,1000,1000,1000,1000,1000,1000,1000,1000,1000,1000,1000,1000,1000,1000,1000,1000,1000,1000,1000,1000]) SharedBlob(0x7f67c8700140 sbid 0x0))
_dump_extent_map csum: [a9c1d499,82e5a14b,13d41153,5d2c92ac,bd486ca7,69b734b3,bbd4506b,5c78934,23a7ec86,71cd4025,da049035,3b335b95,3aaad68e,c108d427,64464011,4e852c8b,f105f7cf,97c530a5,990131c3,53abee5f,eb2a752e,f46c6204,a02cd25e,a0edcf8f,806f4051,6edf9661,3a6a9b6e,46839e5d,47a8fe0,e1fbbc93,2881e5c,ff0c1c78,120aeef4,b871a43b,311a829a,a086216e,690f7afc,2c4fcfc8,5ca3103d,1b26aedc,75e29d22,c6ef70c2,b554bde1,ad70d878,55acfc75,1adb3a0a,8ac031ab,5392bb48,6548b760,7b8223e,9bf5dd1b,8935c0b,d5ba7870,4bb04662,b37a21fc,ab36345c,2277149a,fbb73550,2dc74707,bfafd22b,28981f79,950972b1,d6bbde66,74b66358,81c50f84,716677d5,2b6ef5d2,996752fd,b99bf360,24715cce,d62dfb8,b11bd85c,3136a56a,882e8c4,ecf2eb0c,16926e73,d339b6de,d17d8613,337ca950,cad27fa6,f2efd4e7,bb0b23ce,6c8b014b,209144b7,86da06c3,8e6fa11e,463ec5a,c1b83c22,187d0b9c,15931b79,5dda6148,a89ab9ae,563f9db5,33902e1,cde965c4,859ac4e3,3a2d5134,9a824e29,6e9626a8,f9c58152,647d262a,955ca05d,baaa6a85,58e3133b,a19af4f0,57cdb970,fa0c6a09,551ac600,8400f2b5,2885abc7,9ce677f1,4d3d5310,b8f464a,2693ec2b,bfedcacc,6a302160,2e312a4f,362e6430,9c0d1984,cba58e72,9fe69d47,5ae2db10,f5ebd276,9dbbbc83,a4df126a,f4b63496,4e0034cb,1df47ea7]

提取出关键的pextent的信息:

[root@s131 /data]# cat onode_dump |grep "blob(" |awk '{print $5" "$6" "$7}'
blob([0x86d626d000~80000] csum crc32c/0x1000)
blob([0x86d62ed000~80000] csum crc32c/0x1000)
blob([0x86d636d000~80000] csum crc32c/0x1000)
blob([0x86d63ed000~80000] csum crc32c/0x1000)
blob([0x86d646d000~80000] csum crc32c/0x1000)
blob([0x86d64ed000~21000] csum crc32c/0x1000)
spanning 0 blob([!~21000,0x86d650e000~1000]

[0x86d626d000~80000]表示的是blob中的pextent的数组,0x86d626d000是pextent在裸盘上的offset,80000为其长度
由于笔者的环境比较干净,这些blob的pextent在裸盘上是连续的,用户文件的长度是已知的,为2759239,我们可以通过如下方式提取出用户文件

[root@s131 /data]# printf %lld 0x86d626d000
579118485504
[root@s131 /data]# dd if=/dev/sdb2 of=test_onode_dump bs=1 count=2759239 skip=579118485504
[root@s131 /data]# md5sum /cephfs/ceph-osd.0.log
e07a2ab39136190a9550a3b07ca9efd9 /cephfs/ceph-osd.0.log
[root@s131 /data]# md5sum test_onode_dump
e07a2ab39136190a9550a3b07ca9efd9 test_onode_dump

提取出的文件的md5跟直接通过/cephfs访问得到的mds5一致,提前用户文件数据完毕: )

三、关注笔者

 

最新文章

  1. 解决css3毛玻璃效果(blur)有白边问题
  2. #听云博客大赛#如何在自己的App嵌入听云产品监控App性能
  3. Freemarker中日期时间格式出错
  4. 只需一点小修改,HTC Vive画面会更清晰锐利
  5. Matlab中函数定义方法
  6. js 进度条,可实现结束和重新开始
  7. Java里的if else嵌套语句例子
  8. 清爽绿色格调图文box通用样式
  9. Introducing Microsoft Sync Framework: Sync Services for File Systems
  10. ASP.NET Ajax核心对象
  11. Microsoft Word Regular Expression
  12. hdu4655Cut Pieces
  13. win10 UWP FlipView
  14. .NET Core+MySql+Nginx 容器化部署
  15. php curl实现get和post请求
  16. Centos7.4下安装Jumpserver 1.0.0(支持windows组件)
  17. 导出Excel工具类
  18. jQuery如何判断input元素是否获得焦点(点击编辑时)
  19. git 命令详细介绍
  20. 让运行着的ASP.NET Web程序重新启动

热门文章

  1. Matlab Tricks(二十四)—— 将一副图像逆时针旋转 180°
  2. POJ3723 Conscription 【并检查集合】
  3. Android开源项目SlidingMenu本学习笔记(两)
  4. Angular组件间的数据传输
  5. Binding的三种方式
  6. .NET与Java互通AES算法加密解密
  7. KEIL MDK编译后的代码量和RAM使用详解
  8. GIS基础软件及操作(一)
  9. mysql自动化安装脚本(二进制安装)
  10. 国家气象局 天气预报 城市代码(JSON格式)