1 // -*- mode:C++; tab-width:8; c-basic-offset:2; indent-tabs-mode:t -*-
2 // vim: ts=8 sw=2 smarttab
8 #include "include/types.h"
9 #include "common/Formatter.h"
10 #include "common/ceph_argparse.h"
11 #include "common/errno.h"
12 #include "osdc/Journaler.h"
13 #include "mds/mdstypes.h"
14 #include "mds/LogEvent.h"
15 #include "mds/InoTable.h"
16 #include "mds/CDentry.h"
18 #include "mds/events/ENoOp.h"
19 #include "mds/events/EUpdate.h"
21 #include "mds/JournalPointer.h"
22 // #include "JournalScanner.h"
23 // #include "EventOutput.h"
24 // #include "Dumper.h"
25 // #include "Resetter.h"
27 // #include "JournalTool.h"
29 #include "type_helper.hpp"
30 #include "include/object.h"
32 WRITE_RAW_ENCODER(char)
33 WRITE_RAW_ENCODER(unsigned char)
35 #define dout_context g_ceph_context
36 #define dout_subsys ceph_subsys_mds
38 #define dout_prefix *_dout << __func__ << ": "
41 void MetaTool::meta_op::release()
43 for (const auto& i
: inodes
) {
47 while (!sub_ops
.empty()) {
53 void MetaTool::inode_meta_t::decode_json(JSONObj
*obj
)
55 unsigned long long tmp
;
56 JSONDecoder::decode_json("snapid_t", tmp
, obj
, true);
58 JSONDecoder::decode_json("itype", tmp
, obj
, true);
62 JSONDecoder::decode_json("store", *_i
, obj
, true);
65 void MetaTool::usage()
67 generic_client_usage();
70 int MetaTool::main(string
& mode
,
81 std::string manual_meta_pool
;
82 std::string manual_data_pool
;
83 std::string manual_rank_num
;
84 bool manual_mode
= false;
87 string_split(minfo
, v
);
88 manual_meta_pool
= v
.size() >= 1 ? v
[0] : "";
89 manual_data_pool
= v
.size() >= 2 ? v
[1] : "";
90 manual_rank_num
= v
.size() >= 3 ? v
[2] : "";
91 std::cout
<< "("<< minfo
<< ")=>"
92 << " mpool: " << manual_meta_pool
93 << " dpool: " << manual_data_pool
94 << " rank: " << manual_rank_num
96 if (!manual_meta_pool
.empty() && !manual_data_pool
.empty() && !manual_rank_num
.empty()) {
97 std::cout
<< "you specify rank: " << manual_rank_num
98 << " mpool: " << manual_meta_pool
99 << " dpool: " << manual_data_pool
100 << "\nstart manual mode!!"<< std::endl
;
106 r
= rados
.init_with_context(g_ceph_context
);
108 cerr
<< "RADOS unavailable" << std::endl
;
113 cout
<< "MetaTool: connecting to RADOS..." << std::endl
;
116 cerr
<< "couldn't connect to cluster: " << cpp_strerror(r
) << std::endl
;
121 r
= role_selector
.parse(*fsmap
, rank_str
);
123 cerr
<< "Couldn't determine MDS rank." << std::endl
;
127 auto fs
= fsmap
->get_filesystem(role_selector
.get_ns());
128 assert(fs
!= nullptr);
130 // prepare io for meta pool
131 int64_t const pool_id
= fs
->mds_map
.get_metadata_pool();
132 features
= fs
->mds_map
.get_up_features();
134 features
= CEPH_FEATURES_SUPPORTED_DEFAULT
;
135 else if (features
!= CEPH_FEATURES_SUPPORTED_DEFAULT
) {
136 cout
<< "I think we need to check the feature! : " << features
<< std::endl
;
140 std::string pool_name
;
141 r
= rados
.pool_reverse_lookup(pool_id
, &pool_name
);
143 cerr
<< "Pool " << pool_id
<< " named in MDS map not found in RADOS!" << std::endl
;
148 cout
<< "MetaTool: creating IoCtx.." << std::endl
;
149 r
= rados
.ioctx_create(pool_name
.c_str(), io_meta
);
153 // prepare io for data pool
154 for (const auto p
: fs
->mds_map
.get_data_pools()) {
155 r
= rados
.pool_reverse_lookup(p
, &pool_name
);
157 cerr
<< "Pool " << pool_id
<< " named in MDS map not found in RADOS!" << std::endl
;
160 librados::IoCtx
* io_data
= new librados::IoCtx
;
161 r
= rados
.ioctx_create(pool_name
.c_str(), *io_data
);
163 io_data_v
.push_back(io_data
);
166 for (auto role
: role_selector
.get_roles()) {
169 r
= process(mode
, ino
, out
, in
, confirm
);
170 cout
<< "executing for rank " << rank
<< " op[" <<mode
<< "] ret : " << r
<< std::endl
;
174 features
= CEPH_FEATURES_SUPPORTED_DEFAULT
;
175 r
= rados
.ioctx_create(manual_meta_pool
.c_str(), io_meta
);
178 librados::IoCtx
* io_data
= new librados::IoCtx
;
179 r
= rados
.ioctx_create(manual_data_pool
.c_str(), *io_data
);
181 io_data_v
.push_back(io_data
);
184 rank
= conv_t
<int>(manual_rank_num
);
185 r
= process(mode
, ino
, out
, in
, confirm
);
186 cout
<< "op[" << mode
<< "] ret : " << r
<< std::endl
;
191 int MetaTool::process(string
& mode
, string
& ino
, string out
, string in
, bool confirm
)
193 if (mode
== "showm") {
194 return show_meta_info(ino
, out
);
195 } else if (mode
== "showfn") {
196 return show_fnode(ino
, out
);
197 } else if (mode
== "listc") {
198 return list_meta_info(ino
, out
);
199 } else if (mode
== "amend") {
200 return amend_meta_info(ino
, in
, confirm
);
201 } else if (mode
== "amendfn") {
202 return amend_fnode(in
, confirm
);
204 cerr
<< "bad command '" << mode
<< "'" << std::endl
;
208 int MetaTool::show_fnode(string
& ino
, string
& out
)
211 inodeno_t i_ino
= std::stoull(ino
.c_str(), nullptr, 0);
212 meta_op
op(_debug
, out
);
213 meta_op::sub_op
* nsop
= new meta_op::sub_op(&op
);
214 nsop
->sub_op_t
= meta_op::OP_SHOW_FN
;
215 nsop
->sub_ino_t
= meta_op::INO_DIR
;
218 return op_process(op
);
220 cerr
<< "parameter error? : ino = " << ino
<< std::endl
;
224 int MetaTool::amend_fnode(string
& in
, bool confirm
)
226 meta_op
op(_debug
, "", in
, confirm
);
227 meta_op::sub_op
* nsop
= new meta_op::sub_op(&op
);
228 nsop
->sub_op_t
= meta_op::OP_AMEND_FN
;
229 nsop
->sub_ino_t
= meta_op::INO_DIR
;
232 return op_process(op
);
234 int MetaTool::amend_meta_info(string
& ino
, string
& in
, bool confirm
)
236 if (ino
!= "0" && in
!= "") {
237 inodeno_t i_ino
= std::stoull(ino
.c_str(), nullptr, 0);
238 meta_op
op(_debug
, "", in
, confirm
);
239 meta_op::sub_op
* nsop
= new meta_op::sub_op(&op
);
240 nsop
->sub_op_t
= meta_op::OP_AMEND
;
241 nsop
->sub_ino_t
= meta_op::INO_DIR
;
244 return op_process(op
);
246 cerr
<< "parameter error? : ino = " << ino
<< std::endl
;
250 int MetaTool::list_meta_info(string
& ino
, string
& out
)
253 inodeno_t i_ino
= std::stoull(ino
.c_str(), nullptr, 0);
254 meta_op
op(_debug
, out
);
255 meta_op::sub_op
* nsop
= new meta_op::sub_op(&op
);
256 nsop
->sub_op_t
= meta_op::OP_LIST
;
257 nsop
->sub_ino_t
= meta_op::INO_DIR
;
260 return op_process(op
);
262 cerr
<< "parameter error? : ino = " << ino
<< std::endl
;
266 int MetaTool::show_meta_info(string
& ino
, string
& out
)
269 inodeno_t i_ino
= std::stoull(ino
.c_str(), nullptr, 0);
270 meta_op
op(_debug
, out
);
272 meta_op::sub_op
* nsop
= new meta_op::sub_op(&op
);
273 nsop
->sub_op_t
= meta_op::OP_SHOW
;
274 nsop
->sub_ino_t
= meta_op::INO_DIR
;
277 return op_process(op
);
279 cerr
<< "parameter error? : ino = " << ino
<< std::endl
;
284 int MetaTool::op_process(meta_op
& op
)
287 while (!op
.no_sops()) {
289 std::cout
<< "process : " << op
.top_op()->detail() << std::endl
;
290 switch(op
.top_op()->sub_op_t
) {
291 case meta_op::OP_LIST
:
294 case meta_op::OP_LTRACE
:
297 case meta_op::OP_SHOW
:
300 case meta_op::OP_AMEND
:
303 case meta_op::OP_SHOW_FN
:
306 case meta_op::OP_AMEND_FN
:
310 cerr
<< "unknow op" << std::endl
;
321 int MetaTool::amend_meta(meta_op
&op
)
323 meta_op::sub_op
* sop
= op
.top_op();
324 auto item
= op
.inodes
.find(sop
->ino
);
325 auto item_k
= op
.okeys
.find(sop
->ino
);
326 if (item
!= op
.inodes
.end() && item_k
!= op
.okeys
.end()) {
327 if (_amend_meta(item_k
->second
, *(item
->second
), op
.infile(), op
) < 0)
330 if (op
.inodes
.empty()) {
331 meta_op::sub_op
* nsop
= new meta_op::sub_op(&op
);
332 nsop
->sub_op_t
= meta_op::OP_LIST
;
333 nsop
->sub_ino_t
= meta_op::INO_DIR
;
334 nsop
->trace_level
= 0;
335 nsop
->ino_c
= sop
->ino
;
345 void MetaTool::inode_meta_t::encode(::ceph::bufferlist
& bl
, uint64_t features
)
349 _i
->encode_bare(bl
, features
);
351 int MetaTool::_amend_meta(string
& k
, inode_meta_t
& inode_meta
, const string
& fn
, meta_op
& op
)
354 if (!parser
.parse(fn
.c_str())) {
355 cout
<< "Error parsing create user response" << std::endl
;
360 inode_meta
.decode_json(&parser
);
361 } catch (JSONDecoder::err
& e
) {
362 cout
<< "failed to decode JSON input: " << e
.what() << std::endl
;
366 if (!op
.confirm_chg() || op
.is_debug()) {
367 cout
<< "you will amend info of inode ==>: " << std::endl
;
368 _show_meta(inode_meta
, "");
371 if (!op
.confirm_chg()) {
372 cout
<< "warning: this operation is irreversibl!!!\n"
373 << " You must confirm that all logs of mds have been flushed!!!\n"
374 << " if you want amend it, please add --yes-i-really-really-mean-it!!!"
380 inode_meta
.encode(bl
, features
);
381 map
<string
, bufferlist
> to_set
;
383 inode_backpointer_t bp
;
384 if (!op
.top_op()->get_ancestor(bp
))
387 auto item
= op
.inodes
.find(bp
.dirino
);
388 if (item
!= op
.inodes
.end()) {
389 frag
= item
->second
->get_meta()->pick_dirfrag(bp
.dname
);
391 string oid
= obj_name(bp
.dirino
, frag
);
392 int ret
= io_meta
.omap_set(oid
, to_set
);
396 int MetaTool::show_fn(meta_op
&op
)
398 meta_op::sub_op
* sop
= op
.top_op();
399 auto item
= op
.inodes
.find(sop
->ino
);
400 if (item
!= op
.inodes
.end()) {
401 if (_show_fn(*(item
->second
), op
.outfile()) < 0)
404 if (op
.inodes
.empty()) {
405 meta_op::sub_op
* nsop
= new meta_op::sub_op(&op
);
406 nsop
->sub_op_t
= meta_op::OP_LIST
;
407 nsop
->sub_ino_t
= meta_op::INO_DIR
;
408 nsop
->trace_level
= 0;
409 nsop
->ino_c
= sop
->ino
;
417 int MetaTool::_show_fn(inode_meta_t
& inode_meta
, const string
& fn
)
419 std::list
<frag_t
> frags
;
420 inode_meta
.get_meta()->dirfragtree
.get_leaves(frags
);
421 std::stringstream ds
;
422 std::string format
= "json";
424 Formatter
* f
= Formatter::create(format
);
425 f
->enable_line_break();
426 f
->open_object_section("fnodes");
427 for (const auto &frag
: frags
) {
429 string oid
= obj_name(inode_meta
.get_meta()->inode
->ino
, frag
);
430 int ret
= io_meta
.omap_get_header(oid
, &hbl
);
432 std::cerr
<< __func__
<< " : can't find oid("<< oid
<< ")" << std::endl
;
438 auto p
= hbl
.cbegin();
439 ::decode(got_fnode
, p
);
440 } catch (const buffer::error
&err
) {
441 cerr
<< "corrupt fnode header in " << oid
442 << ": " << err
.what() << std::endl
;
448 f
->open_object_section(oid
.c_str());
453 f
->dump_string("oids", oids
.c_str());
463 cout
<< "out to file (" << fn
<< ") failed" << std::endl
;
464 cout
<< ds
.str() << std::endl
;
467 std::cout
<< ds
.str() << std::endl
;
470 int MetaTool::amend_fn(meta_op
&op
)
472 if (_amend_fn(op
.infile(), op
.confirm_chg()) < 0)
476 int MetaTool::_amend_fn(const string
& fn
, bool confirm
)
479 if (!parser
.parse(fn
.c_str())) {
480 cout
<< "Error parsing create user response : " << fn
<< std::endl
;
484 cout
<< "warning: this operation is irreversibl!!!\n"
485 << " You must confirm that all logs of mds have been flushed!!!\n"
486 << " if you want amend it, please add --yes-i-really-really-mean-it!!!"
492 JSONDecoder::decode_json("oids", tmp
, &parser
, true);
493 string::size_type pos1
, pos2
;
498 while (string::npos
!= pos2
) {
499 v
.push_back(tmp
.substr(pos1
, pos2
-pos1
));
500 pos1
= pos2
+ c
.size();
501 pos2
= tmp
.find(c
, pos1
);
503 if (pos1
!= tmp
.length())
504 v
.push_back(tmp
.substr(pos1
));
507 cout
<< "amend frag : " << i
<< "..." << std::endl
;
509 JSONDecoder::decode_json(i
.c_str(), fnode
, &parser
, true);
512 ret
= io_meta
.omap_set_header(i
, bl
);
516 } catch (JSONDecoder::err
& e
) {
517 cout
<< "failed to decode JSON input: " << e
.what() << std::endl
;
522 int MetaTool::show_meta(meta_op
&op
)
524 meta_op::sub_op
* sop
= op
.top_op();
525 auto item
= op
.inodes
.find(sop
->ino
);
526 if (item
!= op
.inodes
.end()) {
527 if (_show_meta(*(item
->second
), op
.outfile()) < 0)
530 if (op
.inodes
.empty()) {
531 meta_op::sub_op
* nsop
= new meta_op::sub_op(&op
);
532 nsop
->sub_op_t
= meta_op::OP_LIST
;
533 nsop
->sub_ino_t
= meta_op::INO_DIR
;
534 nsop
->trace_level
= 0;
535 nsop
->ino_c
= sop
->ino
;
544 int MetaTool::_show_meta(inode_meta_t
& inode_meta
, const string
& fn
)
546 std::stringstream ds
;
547 std::string format
= "json";
548 InodeStore
& inode_data
= *inode_meta
.get_meta();
549 Formatter
* f
= Formatter::create(format
);
550 f
->enable_line_break();
551 f
->open_object_section("meta");
552 f
->dump_unsigned("snapid_t", inode_meta
.get_snapid());
553 f
->dump_unsigned("itype", inode_meta
.get_type());
554 f
->open_object_section("store");
557 if (inode_data
.snap_blob
.length()) {
559 auto p
= inode_data
.snap_blob
.cbegin();
561 f
->open_object_section("snap_blob");
565 } catch (const buffer::error
&err
) {
566 cerr
<< "corrupt decode in snap_blob"
567 << ": " << err
.what() << std::endl
;
582 cout
<< "out to file (" << fn
<< ") failed" << std::endl
;
583 cout
<< ds
.str() << std::endl
;
587 std::cout
<< ds
.str() << std::endl
;
590 int MetaTool::list_meta(meta_op
&op
)
592 meta_op::sub_op
* sop
= op
.top_op();
594 bool list_all
= false;
596 inodeno_t ino
= sop
->ino_c
;
597 frag_t frag
= sop
->frag
;
599 if (sop
->ino_c
== 0) {
601 oid
= obj_name(sop
->ino
, frag
);
604 std::cout
<< __func__
<< " : " << sop
->trace_level
<< " " << op
.ancestors
.size() << std::endl
;
605 inode_backpointer_t bp
;
606 if (sop
->get_c_ancestor(bp
)) {
607 auto item
= op
.inodes
.find(bp
.dirino
);
608 if (item
!= op
.inodes
.end()) {
609 frag
= item
->second
->get_meta()->pick_dirfrag(bp
.dname
);
611 oid
= obj_name(bp
.dirino
, frag
);
613 meta_op::sub_op
* nsop
= new meta_op::sub_op(&op
);
614 nsop
->ino
= sop
->ino_c
;
615 nsop
->sub_op_t
= meta_op::OP_LTRACE
;
616 nsop
->sub_ino_t
= meta_op::INO_DIR
;
622 std::cout
<< __func__
<< " : " << string(list_all
?"listall ":"info ") << oid
<< " "<< ino
<< std::endl
;
624 int ret
= io_meta
.omap_get_header(oid
, &hbl
);
626 std::cerr
<< __func__
<< " : can't find it, maybe it (ino:"<< sop
->ino
<< ")isn't a normal dir!" << std::endl
;
630 if (hbl
.length() == 0) { // obj has splite
632 if (frag
== frag_t()) {
633 auto item
= op
.inodes
.find(sop
->ino
);
634 if (item
!= op
.inodes
.end()) {
635 inodeno_t tmp
= sop
->ino
;
637 std::list
<frag_t
> frags
;
638 item
->second
->get_meta()->dirfragtree
.get_leaves(frags
);
639 for (const auto &frag
: frags
) {
640 meta_op::sub_op
* nsop
= new meta_op::sub_op(&op
);
642 nsop
->sub_op_t
= meta_op::OP_LIST
;
643 nsop
->sub_ino_t
= meta_op::INO_DIR
;
648 meta_op::sub_op
* nsop
= new meta_op::sub_op(&op
);
649 nsop
->ino_c
= sop
->ino
;
650 nsop
->sub_op_t
= meta_op::OP_LIST
;
651 nsop
->sub_ino_t
= meta_op::INO_DIR
;
656 cerr
<< __func__
<< " missing some data (" << oid
<< ")???" << std::endl
;
660 if (frag
== frag_t()) {
661 inode_backpointer_t bp
;
662 if (sop
->get_c_ancestor(bp
)) {
663 meta_op::sub_op
* nsop
= new meta_op::sub_op(&op
);
664 nsop
->ino_c
= bp
.dirino
;
665 nsop
->sub_op_t
= meta_op::OP_LIST
;
666 nsop
->sub_ino_t
= meta_op::INO_DIR
;
667 nsop
->trace_level
= sop
->trace_level
+ 1;
671 cerr
<< __func__
<< "can't find obj(" << oid
<< ") ,miss ancestors or miss some objs??? " << std::endl
;
675 cerr
<< __func__
<< "missing some objs(" << oid
<< ")??? " << std::endl
;
683 auto p
= hbl
.cbegin();
684 ::decode(got_fnode
, p
);
685 } catch (const buffer::error
&err
) {
686 cerr
<< "corrupt fnode header in " << oid
687 << ": " << err
.what() << std::endl
;
692 std::string format
= "json";
693 Formatter
* f
= Formatter::create(format
);
694 f
->enable_line_break();
695 f
->dump_string("type", "--fnode--");
696 f
->open_object_section("fnode");
700 std::cout
<< std::endl
;
704 std::map
<string
, bufferlist
> out_vals
;
706 io_meta
.omap_get_vals(oid
, "", max_vals
, &out_vals
);
708 bool force_dirty
= false;
709 const set
<snapid_t
> *snaps
= NULL
;
710 unsigned pos
= out_vals
.size() - 1;
711 std::string last_dname
;
712 for (map
<string
, bufferlist
>::iterator p
= out_vals
.begin();
717 dentry_key_t::decode_helper(p
->first
, dname
, last
);
722 if (show_child(p
->first
, dname
, last
, p
->second
, pos
, snaps
,
723 &force_dirty
, ino
, &op
) == 1) {
727 cout
<< "dname : " << dname
<< " " << last
<< std::endl
;
728 if (show_child(p
->first
, dname
, last
, p
->second
, pos
, snaps
,
732 } catch (const buffer::error
&err
) {
733 derr
<< "Corrupt dentry '" << dname
<< "' : "
734 << err
.what() << "(" << "" << ")" << dendl
;
738 while (out_vals
.size() == (size_t)max_vals
) {
740 io_meta
.omap_get_vals(oid
, last_dname
, max_vals
, &out_vals
);
741 pos
= out_vals
.size() - 1;
742 for (map
<string
, bufferlist
>::iterator p
= (++out_vals
.begin());
747 dentry_key_t::decode_helper(p
->first
, dname
, last
);
751 if (show_child(p
->first
, dname
, last
, p
->second
, pos
, snaps
,
752 &force_dirty
, ino
, &op
) == 1) {
756 cout
<< "dname : " << dname
<< " " << last
<< std::endl
;
757 if (show_child(p
->first
, dname
, last
, p
->second
, pos
, snaps
,
761 } catch (const buffer::error
&err
) {
762 derr
<< "Corrupt dentry '" << dname
<< "' : "
763 << err
.what() << "(" << "" << ")" << dendl
;
770 cerr
<< __func__
<< "miss obj(ino:" << ino
<< ")??? " << std::endl
;
776 int MetaTool::file_meta(meta_op
&op
)
779 if (op
.top_op()->sub_ino_t
== meta_op::INO_DIR
) {
780 r
= _file_meta(op
, io_meta
);
781 } else if (op
.top_op()->sub_ino_t
== meta_op::INO_F
) {
782 for (auto i
= io_data_v
.begin(); i
!= io_data_v
.end(); ++i
)
783 if ((r
= _file_meta(op
, **i
)) == 1)
787 inode_backpointer_t bp
;
788 if (op
.top_op()->get_ancestor(bp
)) {
791 std::cerr
<< "no trace for obj (ino:" << op
.top_op()->ino
<<")??" << std::endl
;
794 } else if (op
.top_op()->sub_ino_t
== meta_op::INO_DIR
) {
795 std::cerr
<< "\tmaybe it's a file(ino:" << op
.top_op()->ino
<< ")" << std::endl
;
796 op
.top_op()->sub_ino_t
= meta_op::INO_F
;
800 std::cerr
<< "can't get (ino:" << op
.top_op()->ino
<<")trace??" << std::endl
;
804 int MetaTool::_file_meta(meta_op
&op
, librados::IoCtx
& io
)
806 inodeno_t ino
= op
.top_op()->ino
;
807 std::string oid
= obj_name(ino
);
808 bufferlist pointer_bl
;
809 std::map
<std::string
, bufferlist
> attrset
;
811 bool have_data
= false;
812 r
= io
.getxattrs (oid
.c_str(), attrset
);
814 std::stringstream ds
;
815 std::string format
= "json";
816 Formatter
* f
= Formatter::create(format
);
817 auto item
= attrset
.find("parent");
818 if (item
!= attrset
.end()) {
819 inode_backtrace_t i_bt
;
821 bufferlist::const_iterator q
= item
->second
.cbegin();
823 f
->open_array_section("info");
825 if (i_bt
.ancestors
.size() > 0)
826 op
.ancestors
[ino
] = i_bt
.ancestors
[0];
827 f
->dump_string("type", "--i_bt--");
828 f
->open_object_section("parent");
831 } catch (buffer::error
&e
) {
832 cerr
<< "failed to decode parent of " << oid
<< std::endl
;
836 cerr
<< oid
<< " in " << io
.get_pool_name() << " , but no parent" << std::endl
;
840 item
= attrset
.find("layout");
841 if (item
!= attrset
.end()) {
842 file_layout_t layout
;
844 auto q
= item
->second
.cbegin();
846 f
->dump_string("type", "--layout--");
847 f
->open_object_section("layout");
851 } catch (buffer::error
&e
) {
852 cerr
<< "failed to decode layout of " << oid
<< std::endl
;
856 cerr
<< oid
<< " in " << io
.get_pool_name() << " , but no layout" << std::endl
;
862 cout
<< ino
<< " : "<< ds
.str() << std::endl
;
868 std::string
MetaTool::obj_name(inodeno_t ino
, uint64_t offset
, const char *suffix
) const
871 snprintf(name
, sizeof(name
), "%llx.%08llx%s", (long long unsigned)ino
, (long long unsigned)offset
, suffix
? suffix
: "");
872 return std::string(name
);
874 std::string
MetaTool::obj_name(inodeno_t ino
, frag_t fg
, const char *suffix
) const
877 snprintf(name
, sizeof(name
), "%llx.%08llx%s", (long long unsigned)ino
, (long long unsigned)fg
, suffix
? suffix
: "");
878 return std::string(name
);
881 std::string
MetaTool::obj_name(const char* ino
, uint64_t offset
, const char *suffix
) const
884 snprintf(name
, sizeof(name
), "%s.%08llx%s", ino
, (long long unsigned)offset
, suffix
? suffix
: "");
885 std::string out
= name
;
886 transform(out
.begin(), out
.end(), out
.begin(),::tolower
);
890 int MetaTool::show_child(std::string_view key
,
891 std::string_view dname
,
895 const std::set
<snapid_t
> *snaps
,
900 bufferlist::const_iterator q
= bl
.cbegin();
910 std::cout
<< pos
<< " type '" << type
<< "' dname '" << dname
911 << " [" << first
<< "," << last
<< "]"
913 // bool stale = false;
914 if (snaps
&& last
!= CEPH_NOSNAP
) {
915 derr
<< "!!!! erro !!!!" << dendl
;
919 // CDentry *dn = NULL;
920 // look for existing dentry for _last_ snap, can't process snap of obj
922 // dn = lookup_exact_snap(dname, last);
924 // dn = lookup(dname, last);
925 if (type
== 'L' || type
== 'l') {
928 unsigned char d_type
;
929 mempool::mds_co::string alternate_name
;
931 CDentry::decode_remote(type
, ino
, d_type
, alternate_name
, q
);
935 std::cout
<< "find hard link : " << ino
<< "," << d_type
<< std::endl
;
940 std::cout
<< "hard link : " << ino
<< "," << d_type
<< std::endl
;
941 } else if (type
== 'I' || type
== 'i') {
943 // load inode data before lookuping up or constructing CInode
944 InodeStore
& inode_data
= *(new InodeStore
);
946 mempool::mds_co::string alternate_name
;
950 decode(alternate_name
, q
);
951 inode_data
.decode(q
);
954 inode_data
.decode_bare(q
);
957 std::stringstream ds
;
958 std::string format
= "json";
959 Formatter
* f
= Formatter::create(format
);
960 f
->enable_line_break();
961 f
->open_object_section("meta");
962 f
->dump_unsigned("snapid_t", first
);
963 f
->dump_unsigned("itype", type
);
964 f
->open_object_section("store");
967 if (inode_data
.snap_blob
.length()) {
969 auto p
= inode_data
.snap_blob
.cbegin();
971 f
->open_object_section("snap_blob");
975 } catch (const buffer::error
&err
) {
976 cerr
<< "corrupt decode in snap_blob"
977 << ": " << err
.what() << std::endl
;
983 if (sp_ino
> 0 && op
!= NULL
&& sp_ino
== inode_data
.inode
->ino
) {
984 inode_meta_t
* tmp
= new inode_meta_t(first
, type
, &inode_data
);
985 op
->inodes
[inode_data
.inode
->ino
] = tmp
;
986 op
->okeys
[inode_data
.inode
->ino
] = key
.data();
993 cout
<< ds
.str() << std::endl
;
996 std::cerr
<< __func__
<< "unknow type : " << dname
<< "," << type
<< std::endl
;