/src/rocksdb/file/line_file_reader.cc
Line | Count | Source (jump to first uncovered line) |
1 | | // Copyright (c) Facebook, Inc. and its affiliates. All Rights Reserved. |
2 | | // This source code is licensed under both the GPLv2 (found in the |
3 | | // COPYING file in the root directory) and Apache 2.0 License |
4 | | // (found in the LICENSE.Apache file in the root directory). |
5 | | |
6 | | #include "file/line_file_reader.h" |
7 | | |
8 | | #include <cstring> |
9 | | |
10 | | #include "monitoring/iostats_context_imp.h" |
11 | | |
12 | | namespace ROCKSDB_NAMESPACE { |
13 | | |
14 | | IOStatus LineFileReader::Create(const std::shared_ptr<FileSystem>& fs, |
15 | | const std::string& fname, |
16 | | const FileOptions& file_opts, |
17 | | std::unique_ptr<LineFileReader>* reader, |
18 | | IODebugContext* dbg, |
19 | 0 | RateLimiter* rate_limiter) { |
20 | 0 | std::unique_ptr<FSSequentialFile> file; |
21 | 0 | IOStatus io_s = fs->NewSequentialFile(fname, file_opts, &file, dbg); |
22 | 0 | if (io_s.ok()) { |
23 | 0 | reader->reset(new LineFileReader( |
24 | 0 | std::move(file), fname, nullptr, |
25 | 0 | std::vector<std::shared_ptr<EventListener>>{}, rate_limiter)); |
26 | 0 | } |
27 | 0 | return io_s; |
28 | 0 | } |
29 | | |
30 | | bool LineFileReader::ReadLine(std::string* out, |
31 | 2.60M | Env::IOPriority rate_limiter_priority) { |
32 | 2.60M | assert(out); |
33 | 2.60M | if (!io_status_.ok()) { |
34 | | // Status should be checked (or permit unchecked) any time we return false. |
35 | 0 | io_status_.MustCheck(); |
36 | 0 | return false; |
37 | 0 | } |
38 | 2.60M | out->clear(); |
39 | 2.61M | for (;;) { |
40 | | // Look for line delimiter |
41 | 2.61M | const char* found = static_cast<const char*>( |
42 | 2.61M | std::memchr(buf_begin_, '\n', buf_end_ - buf_begin_)); |
43 | 2.61M | if (found) { |
44 | 2.59M | size_t len = found - buf_begin_; |
45 | 2.59M | out->append(buf_begin_, len); |
46 | 2.59M | buf_begin_ += len + /*delim*/ 1; |
47 | 2.59M | ++line_number_; |
48 | 2.59M | return true; |
49 | 2.59M | } |
50 | 24.3k | if (at_eof_) { |
51 | 11.8k | io_status_.MustCheck(); |
52 | 11.8k | return false; |
53 | 11.8k | } |
54 | | // else flush and reload buffer |
55 | 12.5k | out->append(buf_begin_, buf_end_ - buf_begin_); |
56 | 12.5k | Slice result; |
57 | 12.5k | io_status_ = |
58 | 12.5k | sfr_.Read(buf_.size(), &result, buf_.data(), rate_limiter_priority); |
59 | 12.5k | IOSTATS_ADD(bytes_read, result.size()); |
60 | 12.5k | if (!io_status_.ok()) { |
61 | 0 | io_status_.MustCheck(); |
62 | 0 | return false; |
63 | 0 | } |
64 | 12.5k | if (result.size() != buf_.size()) { |
65 | | // The obscure way of indicating EOF |
66 | 11.8k | at_eof_ = true; |
67 | 11.8k | } |
68 | 12.5k | buf_begin_ = result.data(); |
69 | 12.5k | buf_end_ = result.data() + result.size(); |
70 | 12.5k | } |
71 | 2.60M | } |
72 | | |
73 | | } // namespace ROCKSDB_NAMESPACE |