| 367 | } |
| 368 | |
| 369 | Future<> AddScanTasks(const std::shared_ptr<FragmentScanner>& fragment_scanner) { |
| 370 | scan_state->fragment_scanner = fragment_scanner; |
| 371 | ScanState* state_view = scan_state.get(); |
| 372 | Future<> list_and_scan_done = Future<>::Make(); |
| 373 | // Finish callback keeps the scan state alive until all scan tasks done |
| 374 | struct StateHolder { |
| 375 | Status operator()() { |
| 376 | list_and_scan_done.MarkFinished(); |
| 377 | return Status::OK(); |
| 378 | } |
| 379 | Future<> list_and_scan_done; |
| 380 | std::unique_ptr<ScanState> scan_state; |
| 381 | }; |
| 382 | |
| 383 | std::unique_ptr<util::AsyncTaskGroup> scan_tasks = util::AsyncTaskGroup::Make( |
| 384 | node->batches_throttle_.get(), |
| 385 | StateHolder{list_and_scan_done, std::move(scan_state)}); |
| 386 | for (int i = 0; i < fragment_scanner->NumBatches(); i++) { |
| 387 | node->num_batches_.fetch_add(1); |
| 388 | scan_tasks->AddTask(std::make_unique<ScanBatchTask>(node, state_view, i)); |
| 389 | } |
| 390 | return Status::OK(); |
| 391 | // The "list fragments" task doesn't actually end until the fragments are |
| 392 | // all scanned. This allows us to enforce fragment readahead. |
| 393 | return list_and_scan_done; |
| 394 | } |
| 395 | |
| 396 | // Take the dataset options, and the fragment evolution, and figure out exactly how |
| 397 | // we should scan the fragment itself. |
nothing calls this directly
no test coverage detected