using namespace std;
void usage(const string &name) {
- cerr << "Usage: " << name << " <log_to_replay> <raw_duplicate|free_dump|try_alloc count want alloc_unit|replay_alloc alloc_list_file|export_binary out_file>" << std::endl;
+ cerr << "Usage: " << name << " <log_to_replay> <raw_duplicates|duplicates|free_dump|try_alloc count want alloc_unit|replay_alloc alloc_list_file|export_binary out_file>" << std::endl;
}
void usage_replay_alloc(const string &name) {
return r;
}
+int check_duplicates(char* fname)
+{
+ interval_set<uint64_t> free_extents;
+ interval_set<uint64_t> invalid_extentsA;
+ interval_set<uint64_t> invalid_extentsB;
+ auto dummy_create_fn =
+ [&](std::string_view alloc_type,
+ int64_t capacity,
+ int64_t alloc_unit,
+ std::string_view alloc_name) {
+ };
+ size_t errors = 0;
+ size_t pos = 0;
+ size_t first_err_pos = 0;
+ auto add_fn = [&](uint64_t offset,
+ uint64_t len) {
+ ++pos;
+ if (free_extents.intersects(offset, len)) {
+ invalid_extentsB.insert(offset, len);
+ ++errors;
+ if (first_err_pos == 0) {
+ first_err_pos = pos;
+ }
+ } else {
+ free_extents.insert(offset, len);
+ }
+ };
+ int r = replay_free_dump_and_apply_raw(
+ fname,
+ dummy_create_fn,
+ add_fn);
+ if (r < 0) {
+ return r;
+ }
+ pos = 0;
+ auto add_fn2 = [&](uint64_t offset,
+ uint64_t len) {
+ ++pos;
+ if (pos < first_err_pos) {
+ if (invalid_extentsB.intersects(offset, len)) {
+ invalid_extentsA.insert(offset, len);
+ }
+ }
+ };
+ r = replay_free_dump_and_apply_raw(
+ fname,
+ dummy_create_fn,
+ add_fn2);
+ ceph_assert(r >= 0);
+ auto itA = invalid_extentsA.begin();
+ auto itB = invalid_extentsB.begin();
+ while (itA != invalid_extentsA.end()) {
+ std::cerr << "error: overlapping extents: " << std::hex
+ << itA.get_start() << "~" << itA.get_end() - itA.get_start()
+ << " vs.";
+ while (itB != invalid_extentsB.end() &&
+ itB.get_start() >= itA.get_start() &&
+ itB.get_end() <= itA.get_end()) {
+ std::cerr << " " << itB.get_start() << "~" << itB.get_end() - itB.get_start();
+ ++itB;
+ }
+ std::cerr << std::dec << std::endl;
+ ++itA;
+ }
+ return r >= 0 ? errors != 0 : r;
+}
+
int main(int argc, char **argv)
{
vector<const char*> args;
usage(argv[0]);
return 1;
}
- if (strcmp(argv[2], "raw_duplicate") == 0) {
+ if (strcmp(argv[2], "raw_duplicates") == 0) {
return replay_and_check_for_duplicate(argv[1]);
} else if (strcmp(argv[2], "free_dump") == 0) {
return replay_free_dump_and_apply(argv[1],
});
} else if (strcmp(argv[2], "export_binary") == 0) {
return export_as_binary(argv[1], argv[3]);
+ } else if (strcmp(argv[2], "duplicates") == 0) {
+ return check_duplicates(argv[1]);
}
}