1
0
mirror of https://github.com/ceph/ceph synced 2025-03-11 02:39:05 +00:00

Merge pull request from tchaikov/wip-11833-crush-dump-tree

mon: add an "osd crush dump tree" command

Reviewed-by: Min Chen <minchen@ubuntukylin.com>
Reviewed-by: Haomai Wang <haomaiwang@gmail.com>
This commit is contained in:
Kefu Chai 2015-06-24 17:39:49 +08:00
commit b097e70732
7 changed files with 136 additions and 0 deletions

View File

@ -699,6 +699,12 @@ Usage::
ceph osd crush show-tunables
Subcommand ``tree`` shows the crush buckets and items in a tree view.
Usage::
ceph osd crush tree
Subcommand ``tunables`` sets crush tunables values to <profile>.
Usage::

View File

@ -1456,6 +1456,56 @@ void CrushWrapper::dump(Formatter *f) const
f->close_section();
}
namespace {
// depth first walker
class TreeDumper {
typedef CrushTreeDumper::Item Item;
const CrushWrapper *crush;
public:
TreeDumper(const CrushWrapper *crush)
: crush(crush) {}
void dump(Formatter *f) {
set<int> roots;
crush->find_roots(roots);
for (set<int>::iterator root = roots.begin(); root != roots.end(); ++root) {
dump_item(Item(*root, 0, crush->get_bucket_weightf(*root)), f);
}
}
private:
void dump_item(const Item& qi, Formatter* f) {
if (qi.is_bucket()) {
f->open_object_section("bucket");
CrushTreeDumper::dump_item_fields(crush, qi, f);
dump_bucket_children(qi, f);
f->close_section();
} else {
f->open_object_section("device");
CrushTreeDumper::dump_item_fields(crush, qi, f);
f->close_section();
}
}
void dump_bucket_children(const Item& parent, Formatter* f) {
f->open_array_section("items");
const int max_pos = crush->get_bucket_size(parent.id);
for (int pos = 0; pos < max_pos; pos++) {
int id = crush->get_bucket_item(parent.id, pos);
float weight = crush->get_bucket_item_weightf(parent.id, pos);
dump_item(Item(id, parent.depth + 1, weight), f);
}
f->close_section();
}
};
}
void CrushWrapper::dump_tree(Formatter *f) const
{
assert(f);
TreeDumper(this).dump(f);
}
void CrushWrapper::dump_tunables(Formatter *f) const
{
f->dump_int("choose_local_tries", get_choose_local_tries());

View File

@ -1060,6 +1060,7 @@ public:
void dump_tunables(Formatter *f) const;
void list_rules(Formatter *f) const;
void dump_tree(ostream *out, Formatter *f) const;
void dump_tree(Formatter *f) const;
static void generate_test_instances(list<CrushWrapper*>& o);
int _get_osd_pool_default_crush_replicated_ruleset(CephContext *cct,

View File

@ -531,6 +531,9 @@ COMMAND("osd crush rule create-erasure " \
COMMAND("osd crush rule rm " \
"name=name,type=CephString,goodchars=[A-Za-z0-9-_.] ", \
"remove crush rule <name>", "osd", "rw", "cli,rest")
COMMAND("osd crush tree",
"dump crush buckets and items in a tree view",
"osd", "r", "cli,rest")
COMMAND("osd setmaxosd " \
"name=newmax,type=CephInt,range=0", \
"set new maximum osd value", "osd", "rw", "cli,rest")

View File

@ -3718,6 +3718,12 @@ stats_out:
f->flush(rs);
rs << "\n";
rdata.append(rs.str());
} else if (prefix == "osd crush tree") {
boost::scoped_ptr<Formatter> f(Formatter::create(format, "json-pretty", "json-pretty"));
f->open_array_section("crush_map_roots");
osdmap.crush->dump_tree(f.get());
f->close_section();
f->flush(rdata);
} else if (prefix == "osd erasure-code-profile ls") {
const map<string,map<string,string> > &profiles =
osdmap.get_erasure_code_profiles();

View File

@ -0,0 +1,62 @@
<?xml version="1.0" encoding="UTF-8"?>
<grammar xmlns="http://relaxng.org/ns/structure/1.0">
<start>
<ref name="crush_map_roots"/>
</start>
<define name="item">
<choice>
<ref name="bucket"/>
<ref name="device"/>
</choice>
</define>
<define name="device">
<element name="device">
<element name="id">
<text/>
</element>
<element name="name">
<text/>
</element>
<element name="type">
<text/>
</element>
<element name="type_id">
<text/>
</element>
<element name="crush_weight">
<text/>
</element>
<element name="depth">
<text/>
</element>
</element>
</define>
<define name="bucket">
<element name="bucket">
<element name="id">
<text/>
</element>
<element name="name">
<text/>
</element>
<element name="type">
<text/>
</element>
<element name="type_id">
<text/>
</element>
<element name="items">
<zeroOrMore>
<ref name="item"/>
</zeroOrMore>
</element>
</element>
</define>
<define name="crush_map_roots">
<element name="crush_map_roots">
<oneOrMore>
<ref name="bucket"/>
</oneOrMore>
</element>
</define>
</grammar>

View File

@ -218,6 +218,14 @@ function TEST_crush_reject_empty() {
./ceph osd setcrushmap -i $empty_map.map || return 1
}
function TEST_crush_tree() {
local dir=$1
run_mon $dir a || return 1
./ceph osd crush tree --format=xml | \
$XMLSTARLET val -e -r test/mon/osd-crush-tree.rng - || return 1
}
main osd-crush "$@"
# Local Variables: