-
Notifications
You must be signed in to change notification settings - Fork 4.2k
GH-39808: [C++][Parquet] Evict pre-buffered row-group bytes after decode #49855
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
base: main
Are you sure you want to change the base?
Changes from all commits
907f440
43dd3f1
008e5b7
ac1d90f
9ac85eb
8cecbea
329eef6
81b96ee
a60afc8
de90ce7
80da747
522f1df
fb5a196
File filter
Filter by extension
Conversations
Jump to
Diff view
Diff view
There are no files selected for viewing
| Original file line number | Diff line number | Diff line change | ||||||||||||||||||||||||||||||||||
|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|
|
|
@@ -18,6 +18,7 @@ | |||||||||||||||||||||||||||||||||||
| #include <algorithm> | ||||||||||||||||||||||||||||||||||||
| #include <atomic> | ||||||||||||||||||||||||||||||||||||
| #include <cmath> | ||||||||||||||||||||||||||||||||||||
| #include <deque> | ||||||||||||||||||||||||||||||||||||
| #include <mutex> | ||||||||||||||||||||||||||||||||||||
| #include <utility> | ||||||||||||||||||||||||||||||||||||
| #include <vector> | ||||||||||||||||||||||||||||||||||||
|
|
@@ -151,11 +152,19 @@ struct ReadRangeCache::Impl { | |||||||||||||||||||||||||||||||||||
| IOContext ctx; | ||||||||||||||||||||||||||||||||||||
| CacheOptions options; | ||||||||||||||||||||||||||||||||||||
|
|
||||||||||||||||||||||||||||||||||||
| // Ordered by offset (so as to find a matching region by binary search) | ||||||||||||||||||||||||||||||||||||
| std::vector<RangeCacheEntry> entries; | ||||||||||||||||||||||||||||||||||||
| // Ordered by offset (so as to find a matching region by binary search). | ||||||||||||||||||||||||||||||||||||
| // Mutation of `entries` and of individual entries' futures must be | ||||||||||||||||||||||||||||||||||||
| // serialized via `entry_mutex`. Every public method that touches either | ||||||||||||||||||||||||||||||||||||
| // acquires the mutex before delegating to the protected *Locked helpers | ||||||||||||||||||||||||||||||||||||
| // below, so both the eager and lazy variants are safe to call concurrently | ||||||||||||||||||||||||||||||||||||
| // from multiple threads. | ||||||||||||||||||||||||||||||||||||
| std::deque<RangeCacheEntry> entries; | ||||||||||||||||||||||||||||||||||||
| std::mutex entry_mutex; | ||||||||||||||||||||||||||||||||||||
|
|
||||||||||||||||||||||||||||||||||||
| virtual ~Impl() = default; | ||||||||||||||||||||||||||||||||||||
|
|
||||||||||||||||||||||||||||||||||||
| // -- Polymorphic hooks. Always called with entry_mutex held. -- | ||||||||||||||||||||||||||||||||||||
|
Comment on lines
165
to
+166
Member
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more.
Suggested change
These comments look more like notes while doing the implementation. |
||||||||||||||||||||||||||||||||||||
|
|
||||||||||||||||||||||||||||||||||||
| // Get the future corresponding to a range | ||||||||||||||||||||||||||||||||||||
| virtual Future<std::shared_ptr<Buffer>> MaybeRead(RangeCacheEntry* entry) { | ||||||||||||||||||||||||||||||||||||
| return entry->future; | ||||||||||||||||||||||||||||||||||||
|
|
@@ -172,46 +181,62 @@ struct ReadRangeCache::Impl { | |||||||||||||||||||||||||||||||||||
| return new_entries; | ||||||||||||||||||||||||||||||||||||
| } | ||||||||||||||||||||||||||||||||||||
|
|
||||||||||||||||||||||||||||||||||||
| // Add the given ranges to the cache, coalescing them where possible | ||||||||||||||||||||||||||||||||||||
| virtual Status Cache(std::vector<ReadRange> ranges) { | ||||||||||||||||||||||||||||||||||||
| // -- Public entry points (acquire entry_mutex, then delegate). -- | ||||||||||||||||||||||||||||||||||||
|
|
||||||||||||||||||||||||||||||||||||
|
Comment on lines
+184
to
+185
Member
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more.
Suggested change
|
||||||||||||||||||||||||||||||||||||
| // Add the given ranges to the cache, coalescing them where possible. | ||||||||||||||||||||||||||||||||||||
| Status Cache(std::vector<ReadRange> ranges) { | ||||||||||||||||||||||||||||||||||||
| ARROW_ASSIGN_OR_RAISE( | ||||||||||||||||||||||||||||||||||||
| ranges, internal::CoalesceReadRanges(std::move(ranges), options.hole_size_limit, | ||||||||||||||||||||||||||||||||||||
| options.range_size_limit)); | ||||||||||||||||||||||||||||||||||||
| std::vector<RangeCacheEntry> new_entries = MakeCacheEntries(ranges); | ||||||||||||||||||||||||||||||||||||
| // Add new entries, themselves ordered by offset | ||||||||||||||||||||||||||||||||||||
| if (entries.size() > 0) { | ||||||||||||||||||||||||||||||||||||
| std::vector<RangeCacheEntry> merged(entries.size() + new_entries.size()); | ||||||||||||||||||||||||||||||||||||
| std::merge(entries.begin(), entries.end(), new_entries.begin(), new_entries.end(), | ||||||||||||||||||||||||||||||||||||
| merged.begin()); | ||||||||||||||||||||||||||||||||||||
| entries = std::move(merged); | ||||||||||||||||||||||||||||||||||||
| } else { | ||||||||||||||||||||||||||||||||||||
| entries = std::move(new_entries); | ||||||||||||||||||||||||||||||||||||
| Status st; | ||||||||||||||||||||||||||||||||||||
| { | ||||||||||||||||||||||||||||||||||||
| std::unique_lock<std::mutex> guard(entry_mutex); | ||||||||||||||||||||||||||||||||||||
| std::vector<RangeCacheEntry> new_entries = MakeCacheEntries(ranges); | ||||||||||||||||||||||||||||||||||||
|
Contributor
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. Does |
||||||||||||||||||||||||||||||||||||
| // Add new entries, themselves ordered by offset | ||||||||||||||||||||||||||||||||||||
| if (entries.size() > 0) { | ||||||||||||||||||||||||||||||||||||
| std::deque<RangeCacheEntry> merged(entries.size() + new_entries.size()); | ||||||||||||||||||||||||||||||||||||
| std::merge(entries.begin(), entries.end(), new_entries.begin(), new_entries.end(), | ||||||||||||||||||||||||||||||||||||
| merged.begin()); | ||||||||||||||||||||||||||||||||||||
| entries = std::move(merged); | ||||||||||||||||||||||||||||||||||||
| } else { | ||||||||||||||||||||||||||||||||||||
| for (auto& entry : new_entries) { | ||||||||||||||||||||||||||||||||||||
| entries.push_back(std::move(entry)); | ||||||||||||||||||||||||||||||||||||
| } | ||||||||||||||||||||||||||||||||||||
| } | ||||||||||||||||||||||||||||||||||||
|
Comment on lines
+196
to
+205
Member
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more.
Suggested change
This might be more efficient.
Contributor
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. Why not to use |
||||||||||||||||||||||||||||||||||||
| } | ||||||||||||||||||||||||||||||||||||
| // Prefetch immediately, regardless of executor availability, if possible | ||||||||||||||||||||||||||||||||||||
| auto st = file->WillNeed(ranges); | ||||||||||||||||||||||||||||||||||||
| // Prefetch immediately, regardless of executor availability, if possible. | ||||||||||||||||||||||||||||||||||||
| // Do this outside the lock: WillNeed() may block on an mmap advise / I/O | ||||||||||||||||||||||||||||||||||||
| // hint and we don't want to serialize concurrent Reads on it. | ||||||||||||||||||||||||||||||||||||
| st = file->WillNeed(ranges); | ||||||||||||||||||||||||||||||||||||
| // As this is optimisation only, I/O failures should not be treated as fatal | ||||||||||||||||||||||||||||||||||||
| if (st.IsIOError()) { | ||||||||||||||||||||||||||||||||||||
| return Status::OK(); | ||||||||||||||||||||||||||||||||||||
| } | ||||||||||||||||||||||||||||||||||||
| return st; | ||||||||||||||||||||||||||||||||||||
| } | ||||||||||||||||||||||||||||||||||||
|
|
||||||||||||||||||||||||||||||||||||
| // Read the given range from the cache, blocking if needed. Cannot read a range | ||||||||||||||||||||||||||||||||||||
| // that spans cache entries. | ||||||||||||||||||||||||||||||||||||
| virtual Result<std::shared_ptr<Buffer>> Read(ReadRange range) { | ||||||||||||||||||||||||||||||||||||
| // Read the given range from the cache, blocking if needed. Cannot read a | ||||||||||||||||||||||||||||||||||||
| // range that spans cache entries. | ||||||||||||||||||||||||||||||||||||
| Result<std::shared_ptr<Buffer>> Read(ReadRange range) { | ||||||||||||||||||||||||||||||||||||
| if (range.length == 0) { | ||||||||||||||||||||||||||||||||||||
| static const uint8_t byte = 0; | ||||||||||||||||||||||||||||||||||||
| return std::make_shared<Buffer>(&byte, 0); | ||||||||||||||||||||||||||||||||||||
| } | ||||||||||||||||||||||||||||||||||||
|
|
||||||||||||||||||||||||||||||||||||
| const auto it = std::lower_bound( | ||||||||||||||||||||||||||||||||||||
| entries.begin(), entries.end(), range, | ||||||||||||||||||||||||||||||||||||
| [](const RangeCacheEntry& entry, const ReadRange& range) { | ||||||||||||||||||||||||||||||||||||
| return entry.range.offset + entry.range.length < range.offset + range.length; | ||||||||||||||||||||||||||||||||||||
| }); | ||||||||||||||||||||||||||||||||||||
| if (it != entries.end() && it->range.Contains(range)) { | ||||||||||||||||||||||||||||||||||||
| auto fut = MaybeRead(&*it); | ||||||||||||||||||||||||||||||||||||
| ARROW_ASSIGN_OR_RAISE(auto buf, fut.result()); | ||||||||||||||||||||||||||||||||||||
| Future<std::shared_ptr<Buffer>> fut; | ||||||||||||||||||||||||||||||||||||
| int64_t slice_offset = 0; | ||||||||||||||||||||||||||||||||||||
| { | ||||||||||||||||||||||||||||||||||||
| std::unique_lock<std::mutex> guard(entry_mutex); | ||||||||||||||||||||||||||||||||||||
| const auto it = std::lower_bound( | ||||||||||||||||||||||||||||||||||||
| entries.begin(), entries.end(), range, | ||||||||||||||||||||||||||||||||||||
| [](const RangeCacheEntry& entry, const ReadRange& range) { | ||||||||||||||||||||||||||||||||||||
| return entry.range.offset + entry.range.length < range.offset + range.length; | ||||||||||||||||||||||||||||||||||||
| }); | ||||||||||||||||||||||||||||||||||||
| if (it == entries.end() || !it->range.Contains(range)) { | ||||||||||||||||||||||||||||||||||||
| return Status::Invalid("ReadRangeCache did not find matching cache entry"); | ||||||||||||||||||||||||||||||||||||
| } | ||||||||||||||||||||||||||||||||||||
| fut = MaybeRead(&*it); | ||||||||||||||||||||||||||||||||||||
| slice_offset = range.offset - it->range.offset; | ||||||||||||||||||||||||||||||||||||
| if (options.lazy && options.prefetch_limit > 0) { | ||||||||||||||||||||||||||||||||||||
| int64_t num_prefetched = 0; | ||||||||||||||||||||||||||||||||||||
| for (auto next_it = it + 1; | ||||||||||||||||||||||||||||||||||||
|
|
@@ -224,53 +249,80 @@ struct ReadRangeCache::Impl { | |||||||||||||||||||||||||||||||||||
| ++num_prefetched; | ||||||||||||||||||||||||||||||||||||
| } | ||||||||||||||||||||||||||||||||||||
| } | ||||||||||||||||||||||||||||||||||||
| return SliceBuffer(std::move(buf), range.offset - it->range.offset, range.length); | ||||||||||||||||||||||||||||||||||||
| } | ||||||||||||||||||||||||||||||||||||
| return Status::Invalid("ReadRangeCache did not find matching cache entry"); | ||||||||||||||||||||||||||||||||||||
| // Drop the lock before blocking on the I/O future so other threads can | ||||||||||||||||||||||||||||||||||||
| // still do lookups while a previously queued read is in flight. | ||||||||||||||||||||||||||||||||||||
| ARROW_ASSIGN_OR_RAISE(auto buf, fut.result()); | ||||||||||||||||||||||||||||||||||||
| return SliceBuffer(std::move(buf), slice_offset, range.length); | ||||||||||||||||||||||||||||||||||||
| } | ||||||||||||||||||||||||||||||||||||
|
|
||||||||||||||||||||||||||||||||||||
| virtual Future<> Wait() { | ||||||||||||||||||||||||||||||||||||
| Future<> Wait() { | ||||||||||||||||||||||||||||||||||||
| std::vector<Future<>> futures; | ||||||||||||||||||||||||||||||||||||
| for (auto& entry : entries) { | ||||||||||||||||||||||||||||||||||||
| futures.emplace_back(MaybeRead(&entry)); | ||||||||||||||||||||||||||||||||||||
| { | ||||||||||||||||||||||||||||||||||||
| std::unique_lock<std::mutex> guard(entry_mutex); | ||||||||||||||||||||||||||||||||||||
| futures.reserve(entries.size()); | ||||||||||||||||||||||||||||||||||||
| for (auto& entry : entries) { | ||||||||||||||||||||||||||||||||||||
| futures.emplace_back(MaybeRead(&entry)); | ||||||||||||||||||||||||||||||||||||
| } | ||||||||||||||||||||||||||||||||||||
| } | ||||||||||||||||||||||||||||||||||||
| return AllComplete(futures); | ||||||||||||||||||||||||||||||||||||
| } | ||||||||||||||||||||||||||||||||||||
|
|
||||||||||||||||||||||||||||||||||||
| // Cached ranges are sorted and non-overlapping, so entries ending at or | ||||||||||||||||||||||||||||||||||||
| // before `end_offset` form a prefix. Keep a straddling entry. | ||||||||||||||||||||||||||||||||||||
| int64_t EvictEntriesBefore(int64_t end_offset) { | ||||||||||||||||||||||||||||||||||||
| std::unique_lock<std::mutex> guard(entry_mutex); | ||||||||||||||||||||||||||||||||||||
| int64_t n_evicted = 0; | ||||||||||||||||||||||||||||||||||||
| while (!entries.empty()) { | ||||||||||||||||||||||||||||||||||||
| const auto& range = entries.front().range; | ||||||||||||||||||||||||||||||||||||
| if (range.offset + range.length > end_offset) { | ||||||||||||||||||||||||||||||||||||
| break; | ||||||||||||||||||||||||||||||||||||
| } | ||||||||||||||||||||||||||||||||||||
| entries.pop_front(); | ||||||||||||||||||||||||||||||||||||
| ++n_evicted; | ||||||||||||||||||||||||||||||||||||
| } | ||||||||||||||||||||||||||||||||||||
|
Comment on lines
+275
to
+283
Contributor
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more.
Suggested change
You can determine the quantity first, and then delete them all at once. |
||||||||||||||||||||||||||||||||||||
| return n_evicted; | ||||||||||||||||||||||||||||||||||||
|
Member
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. Would it be more useful to return total evicted memory? |
||||||||||||||||||||||||||||||||||||
| } | ||||||||||||||||||||||||||||||||||||
|
|
||||||||||||||||||||||||||||||||||||
| // Return a Future that completes when the given ranges have been read. | ||||||||||||||||||||||||||||||||||||
| virtual Future<> WaitFor(std::vector<ReadRange> ranges) { | ||||||||||||||||||||||||||||||||||||
| Future<> WaitFor(std::vector<ReadRange> ranges) { | ||||||||||||||||||||||||||||||||||||
| auto end = std::remove_if(ranges.begin(), ranges.end(), | ||||||||||||||||||||||||||||||||||||
| [](const ReadRange& range) { return range.length == 0; }); | ||||||||||||||||||||||||||||||||||||
| ranges.resize(end - ranges.begin()); | ||||||||||||||||||||||||||||||||||||
| std::vector<Future<>> futures; | ||||||||||||||||||||||||||||||||||||
| futures.reserve(ranges.size()); | ||||||||||||||||||||||||||||||||||||
| for (auto& range : ranges) { | ||||||||||||||||||||||||||||||||||||
| const auto it = std::lower_bound( | ||||||||||||||||||||||||||||||||||||
| entries.begin(), entries.end(), range, | ||||||||||||||||||||||||||||||||||||
| [](const RangeCacheEntry& entry, const ReadRange& range) { | ||||||||||||||||||||||||||||||||||||
| return entry.range.offset + entry.range.length < range.offset + range.length; | ||||||||||||||||||||||||||||||||||||
| }); | ||||||||||||||||||||||||||||||||||||
| if (it != entries.end() && it->range.Contains(range)) { | ||||||||||||||||||||||||||||||||||||
| futures.push_back(Future<>(MaybeRead(&*it))); | ||||||||||||||||||||||||||||||||||||
| } else { | ||||||||||||||||||||||||||||||||||||
| return Status::Invalid("Range was not requested for caching: offset=", | ||||||||||||||||||||||||||||||||||||
| range.offset, " length=", range.length); | ||||||||||||||||||||||||||||||||||||
| { | ||||||||||||||||||||||||||||||||||||
| std::unique_lock<std::mutex> guard(entry_mutex); | ||||||||||||||||||||||||||||||||||||
| for (auto& range : ranges) { | ||||||||||||||||||||||||||||||||||||
| const auto it = | ||||||||||||||||||||||||||||||||||||
| std::lower_bound(entries.begin(), entries.end(), range, | ||||||||||||||||||||||||||||||||||||
| [](const RangeCacheEntry& entry, const ReadRange& range) { | ||||||||||||||||||||||||||||||||||||
| return entry.range.offset + entry.range.length < | ||||||||||||||||||||||||||||||||||||
| range.offset + range.length; | ||||||||||||||||||||||||||||||||||||
| }); | ||||||||||||||||||||||||||||||||||||
| if (it != entries.end() && it->range.Contains(range)) { | ||||||||||||||||||||||||||||||||||||
| futures.push_back(Future<>(MaybeRead(&*it))); | ||||||||||||||||||||||||||||||||||||
| } else { | ||||||||||||||||||||||||||||||||||||
| return Status::Invalid("Range was not requested for caching: offset=", | ||||||||||||||||||||||||||||||||||||
| range.offset, " length=", range.length); | ||||||||||||||||||||||||||||||||||||
| } | ||||||||||||||||||||||||||||||||||||
| } | ||||||||||||||||||||||||||||||||||||
| } | ||||||||||||||||||||||||||||||||||||
| return AllComplete(futures); | ||||||||||||||||||||||||||||||||||||
| } | ||||||||||||||||||||||||||||||||||||
| }; | ||||||||||||||||||||||||||||||||||||
|
|
||||||||||||||||||||||||||||||||||||
| // Don't read ranges when they're first added. Instead, wait until they're requested | ||||||||||||||||||||||||||||||||||||
| // (either through Read or WaitFor). | ||||||||||||||||||||||||||||||||||||
| // Don't read ranges when they're first added. Instead, wait until they're | ||||||||||||||||||||||||||||||||||||
| // requested (either through Read or WaitFor). Thread safety is inherited from | ||||||||||||||||||||||||||||||||||||
| // the base Impl: both MakeCacheEntries and MaybeRead are only ever invoked | ||||||||||||||||||||||||||||||||||||
| // from the public entry points, and those hold the base class's entry_mutex | ||||||||||||||||||||||||||||||||||||
| // before delegating. | ||||||||||||||||||||||||||||||||||||
| struct ReadRangeCache::LazyImpl : public ReadRangeCache::Impl { | ||||||||||||||||||||||||||||||||||||
| // Protect against concurrent modification of entries[i]->future | ||||||||||||||||||||||||||||||||||||
| std::mutex entry_mutex; | ||||||||||||||||||||||||||||||||||||
|
|
||||||||||||||||||||||||||||||||||||
| virtual ~LazyImpl() = default; | ||||||||||||||||||||||||||||||||||||
|
|
||||||||||||||||||||||||||||||||||||
| Future<std::shared_ptr<Buffer>> MaybeRead(RangeCacheEntry* entry) override { | ||||||||||||||||||||||||||||||||||||
| // Called by superclass Read()/WaitFor() so we have the lock | ||||||||||||||||||||||||||||||||||||
| // Called by the superclass under entry_mutex, so it is safe to mutate | ||||||||||||||||||||||||||||||||||||
| // entry->future here. | ||||||||||||||||||||||||||||||||||||
| if (!entry->future.is_valid()) { | ||||||||||||||||||||||||||||||||||||
| entry->future = file->ReadAsync(ctx, entry->range.offset, entry->range.length); | ||||||||||||||||||||||||||||||||||||
| } | ||||||||||||||||||||||||||||||||||||
|
|
@@ -288,26 +340,6 @@ struct ReadRangeCache::LazyImpl : public ReadRangeCache::Impl { | |||||||||||||||||||||||||||||||||||
| } | ||||||||||||||||||||||||||||||||||||
| return new_entries; | ||||||||||||||||||||||||||||||||||||
| } | ||||||||||||||||||||||||||||||||||||
|
|
||||||||||||||||||||||||||||||||||||
| Status Cache(std::vector<ReadRange> ranges) override { | ||||||||||||||||||||||||||||||||||||
| std::unique_lock<std::mutex> guard(entry_mutex); | ||||||||||||||||||||||||||||||||||||
| return ReadRangeCache::Impl::Cache(std::move(ranges)); | ||||||||||||||||||||||||||||||||||||
| } | ||||||||||||||||||||||||||||||||||||
|
|
||||||||||||||||||||||||||||||||||||
| Result<std::shared_ptr<Buffer>> Read(ReadRange range) override { | ||||||||||||||||||||||||||||||||||||
| std::unique_lock<std::mutex> guard(entry_mutex); | ||||||||||||||||||||||||||||||||||||
| return ReadRangeCache::Impl::Read(range); | ||||||||||||||||||||||||||||||||||||
| } | ||||||||||||||||||||||||||||||||||||
|
|
||||||||||||||||||||||||||||||||||||
| Future<> Wait() override { | ||||||||||||||||||||||||||||||||||||
| std::unique_lock<std::mutex> guard(entry_mutex); | ||||||||||||||||||||||||||||||||||||
| return ReadRangeCache::Impl::Wait(); | ||||||||||||||||||||||||||||||||||||
| } | ||||||||||||||||||||||||||||||||||||
|
|
||||||||||||||||||||||||||||||||||||
| Future<> WaitFor(std::vector<ReadRange> ranges) override { | ||||||||||||||||||||||||||||||||||||
| std::unique_lock<std::mutex> guard(entry_mutex); | ||||||||||||||||||||||||||||||||||||
| return ReadRangeCache::Impl::WaitFor(std::move(ranges)); | ||||||||||||||||||||||||||||||||||||
| } | ||||||||||||||||||||||||||||||||||||
| }; | ||||||||||||||||||||||||||||||||||||
|
|
||||||||||||||||||||||||||||||||||||
| ReadRangeCache::ReadRangeCache(std::shared_ptr<RandomAccessFile> owned_file, | ||||||||||||||||||||||||||||||||||||
|
|
@@ -336,6 +368,10 @@ Future<> ReadRangeCache::WaitFor(std::vector<ReadRange> ranges) { | |||||||||||||||||||||||||||||||||||
| return impl_->WaitFor(std::move(ranges)); | ||||||||||||||||||||||||||||||||||||
| } | ||||||||||||||||||||||||||||||||||||
|
|
||||||||||||||||||||||||||||||||||||
| int64_t ReadRangeCache::EvictEntriesBefore(int64_t end_offset) { | ||||||||||||||||||||||||||||||||||||
| return impl_->EvictEntriesBefore(end_offset); | ||||||||||||||||||||||||||||||||||||
| } | ||||||||||||||||||||||||||||||||||||
|
|
||||||||||||||||||||||||||||||||||||
| } // namespace internal | ||||||||||||||||||||||||||||||||||||
| } // namespace io | ||||||||||||||||||||||||||||||||||||
| } // namespace arrow | ||||||||||||||||||||||||||||||||||||
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
No strong opinion. I would prefer simplifying comments like this.