in src/native/io/reader.cpp [62:114]
reader reader::chained_reader_impl::slice(uint64_t offset, uint64_t length) const
{
std::vector<reader> readers;
auto lower_bound = std::lower_bound(m_offsets.begin(), m_offsets.end(), offset);
if (lower_bound < m_offsets.begin())
{
std::string msg = "reader::chained_reader_impl::slice(): lower_bound too low. lower_bound: "
+ std::to_string(*lower_bound) + ", m_offset.begin(): " + std::to_string(*m_offsets.begin());
throw errors::user_exception(errors::error_code::io_reader_slice_bound_error, msg);
}
auto index = static_cast<size_t>(lower_bound - m_offsets.begin());
if (index != 0)
{
// This is past the last offset value, try last reader.
if (index >= m_offsets.size())
{
index = m_offsets.size() - 1;
}
else if (offset < m_offsets[index])
{
index--;
}
}
uint64_t offset_in_reader = offset - m_offsets[index];
auto remaining = length;
while ((remaining > 0) && (index < m_readers.size()))
{
auto &reader = m_readers[index];
auto reader_bytes_consumed = std::min(reader.size() - offset_in_reader, remaining);
// If we're not taking the entire reader, then take a slice
if (offset_in_reader || (reader_bytes_consumed < reader.size()))
{
readers.push_back(reader.slice(offset_in_reader, reader_bytes_consumed));
}
else
{
readers.push_back(reader);
}
remaining -= reader_bytes_consumed;
offset_in_reader = 0;
index++;
}
return reader::chain(readers);
}