sstables: Add delete func to rename TOC ensuring table is marked dead
Note: "normal" remove_by_toc_name must now be prepared for and check if the TOC of the sstable is already moved to temp file when we get to the juicy delete parts. Message-Id: <1458575440-505-1-git-send-email-calle@scylladb.com>
This commit is contained in:
committed by
Pekka Enberg
parent
6fd6e57e80
commit
4e52b41a46
Notes:
Avi Kivity
2016-03-26 22:06:40 +03:00
backport: 1.0
@@ -1800,16 +1800,23 @@ fsync_directory(sstring fname) {
|
||||
future<>
|
||||
remove_by_toc_name(sstring sstable_toc_name) {
|
||||
return seastar::async([sstable_toc_name] {
|
||||
auto dir = dirname(sstable_toc_name);
|
||||
auto toc_file = open_checked_file_dma(sstable_read_error, sstable_toc_name, open_flags::ro).get0();
|
||||
sstring prefix = sstable_toc_name.substr(0, sstable_toc_name.size() - TOC_SUFFIX.size());
|
||||
auto new_toc_name = prefix + TEMPORARY_TOC_SUFFIX;
|
||||
sstring dir;
|
||||
|
||||
if (sstable_write_io_check(file_exists, sstable_toc_name).get0()) {
|
||||
dir = dirname(sstable_toc_name);
|
||||
sstable_write_io_check(rename_file, sstable_toc_name, new_toc_name).get();
|
||||
sstable_write_io_check(fsync_directory, dir).get();
|
||||
} else {
|
||||
dir = dirname(new_toc_name);
|
||||
}
|
||||
|
||||
auto toc_file = open_checked_file_dma(sstable_read_error, new_toc_name, open_flags::ro).get0();
|
||||
auto in = make_file_input_stream(toc_file);
|
||||
auto size = toc_file.size().get0();
|
||||
auto text = in.read_exactly(size).get0();
|
||||
in.close().get();
|
||||
sstring prefix = sstable_toc_name.substr(0, sstable_toc_name.size() - TOC_SUFFIX.size());
|
||||
auto new_toc_name = prefix + TEMPORARY_TOC_SUFFIX;
|
||||
sstable_write_io_check(rename_file, sstable_toc_name, new_toc_name).get();
|
||||
sstable_write_io_check(fsync_directory, dir).get();
|
||||
std::vector<sstring> components;
|
||||
sstring all(text.begin(), text.end());
|
||||
boost::split(components, all, boost::is_any_of("\n"));
|
||||
@@ -1829,6 +1836,39 @@ remove_by_toc_name(sstring sstable_toc_name) {
|
||||
});
|
||||
}
|
||||
|
||||
future<>
|
||||
sstable::mark_for_deletion_on_disk() {
|
||||
mark_for_deletion();
|
||||
|
||||
auto toc_name = filename(component_type::TOC);
|
||||
auto shard = std::hash<sstring>()(toc_name) % smp::count;
|
||||
|
||||
return smp::submit_to(shard, [toc_name] {
|
||||
static thread_local std::unordered_set<sstring> renaming;
|
||||
|
||||
if (renaming.count(toc_name) > 0) {
|
||||
return make_ready_future<>();
|
||||
}
|
||||
|
||||
renaming.emplace(toc_name);
|
||||
|
||||
return seastar::async([toc_name] {
|
||||
if (!sstable_write_io_check(file_exists, toc_name).get0()) {
|
||||
return; // already gone
|
||||
}
|
||||
|
||||
auto dir = dirname(toc_name);
|
||||
auto toc_file = open_checked_file_dma(sstable_read_error, toc_name, open_flags::ro).get0();
|
||||
sstring prefix = toc_name.substr(0, toc_name.size() - TOC_SUFFIX.size());
|
||||
auto new_toc_name = prefix + TEMPORARY_TOC_SUFFIX;
|
||||
sstable_write_io_check(rename_file, toc_name, new_toc_name).get();
|
||||
sstable_write_io_check(fsync_directory, dir).get();
|
||||
}).finally([toc_name] {
|
||||
renaming.erase(toc_name);
|
||||
});
|
||||
});
|
||||
}
|
||||
|
||||
future<>
|
||||
sstable::remove_sstable_with_temp_toc(sstring ks, sstring cf, sstring dir, int64_t generation, version_types v, format_types f) {
|
||||
return seastar::async([ks, cf, dir, generation, v, f] {
|
||||
|
||||
@@ -245,6 +245,8 @@ public:
|
||||
_marked_for_deletion = true;
|
||||
}
|
||||
|
||||
future<> mark_for_deletion_on_disk();
|
||||
|
||||
bool marked_for_deletion() const {
|
||||
return _marked_for_deletion;
|
||||
}
|
||||
|
||||
Reference in New Issue
Block a user