crush: fix potential class id collision

Signed-off-by: xie xingguo <xie.xingguo@zte.com.cn>
This commit is contained in:
xie xingguo 2017-06-27 20:24:59 +08:00
parent d54722f6ad
commit 906f0b5bcd
2 changed files with 28 additions and 1 deletions

View File

@ -1283,6 +1283,31 @@ int CrushWrapper::trim_roots_with_class(bool unused)
return 0;
}
int32_t CrushWrapper::_alloc_class_id() const {
if (class_name.empty()) {
return 0;
}
int32_t class_id = class_name.rbegin()->first + 1;
if (class_id >= 0) {
return class_id;
}
// wrapped, pick a random start and do exhaustive search
uint32_t upperlimit = numeric_limits<int32_t>::max() + 1;
class_id = rand() % upperlimit;
const auto start = class_id;
do {
if (!class_name.count(class_id)) {
return class_id;
} else {
class_id++;
if (class_id < 0) {
class_id = 0;
}
}
} while (class_id != start);
assert(0 == "no available class id");
}
void CrushWrapper::reweight(CephContext *cct)
{
set<int> roots;

View File

@ -482,10 +482,12 @@ public:
return 0;
}
int32_t _alloc_class_id() const;
int get_or_create_class_id(const string& name) {
int c = get_class_id(name);
if (c < 0) {
int i = class_name.size();
int i = _alloc_class_id();
class_name[i] = name;
class_rname[name] = i;
return i;