void seek_and_read_getc(concurrency::streams::istream stream, const std::vector<uint8_t>& content_to_compare)
{
    size_t content_len = (int)content_to_compare.size();
    size_t pos1 = 0;
    size_t pos2 = content_len / 4;
    size_t pos3 = content_len / 2;
    size_t pos4 = content_len - content_len / 4;

    std::vector<uint8_t> buffer;
    buffer.resize(content_len);

    CHECK_EQUAL(pos2, stream.seek((int)pos2, std::ios_base::beg));
    for (size_t i = pos2; i < pos3; ++i)
    {
        buffer[i] = (uint8_t)stream.read().get();
    }

    CHECK_EQUAL(pos1, stream.seek((int)(pos1 - pos3), std::ios_base::cur));
    for (size_t i = pos1; i < pos2; ++i)
    {
        buffer[i] = (uint8_t)stream.read().get();
    }

    CHECK_EQUAL(pos3, stream.seek((int)(pos3 - content_len), std::ios_base::end));
    for (size_t i = pos3; i < pos4; ++i)
    {
        buffer[i] = (uint8_t)stream.read().get();
    }

    CHECK_EQUAL(pos4, stream.seek((int)(pos4 - content_len), std::ios_base::end));
    for (size_t i = pos4; i < content_len; ++i)
    {
        buffer[i] = (uint8_t)stream.read().get();
    }

    CHECK_ARRAY_EQUAL(content_to_compare.data(), buffer.data(), (int)content_to_compare.size());
}
void seek_and_read_getn(concurrency::streams::istream stream, const std::vector<uint8_t>& content_to_compare)
{
    size_t content_len = content_to_compare.size();
    size_t pos1 = 0;
    size_t pos2 = content_len / 4;
    size_t pos3 = content_len / 2;
    size_t pos4 = content_len - content_len / 4;

    std::vector<uint8_t> buffer;
    buffer.resize(content_len);
    concurrency::streams::container_buffer<std::vector<uint8_t>> sbuf(buffer, std::ios_base::out);

    sbuf.seekpos(pos3, std::ios_base::out);
    CHECK_EQUAL(pos3, stream.seek((int)pos3, std::ios_base::beg));
    CHECK_EQUAL(pos4 - pos3, stream.read(sbuf, pos4 - pos3).get());

    sbuf.seekpos(pos1, std::ios_base::out);
    CHECK_EQUAL(pos1, stream.seek((int)(pos1 - pos4), std::ios_base::cur));
    CHECK_EQUAL(pos2 - pos1, stream.read(sbuf, pos2 - pos1).get());

    sbuf.seekpos(pos2, std::ios_base::out);
    CHECK_EQUAL(pos2, stream.seek((int)(pos2 - content_len), std::ios_base::end));
    CHECK_EQUAL(pos3 - pos2, stream.read(sbuf, pos3 - pos2).get());

    sbuf.seekpos(pos4, std::ios_base::out);
    CHECK_EQUAL(pos4, stream.seek((int)(pos4 - pos3), std::ios_base::cur));
    CHECK_EQUAL(content_len - pos4, stream.read(sbuf, content_len - pos4).get());

    CHECK_ARRAY_EQUAL(content_to_compare.data(), sbuf.collection().data(), (int)content_len);

    CHECK_EQUAL((concurrency::streams::istream::pos_type)concurrency::streams::istream::traits::eof(), stream.seek(-1, std::ios_base::beg));
    CHECK_EQUAL((concurrency::streams::istream::pos_type)0, stream.seek(0, std::ios_base::beg));
    CHECK_EQUAL((concurrency::streams::istream::pos_type)content_len, stream.seek(0, std::ios_base::end));
    CHECK_EQUAL((concurrency::streams::istream::pos_type)concurrency::streams::istream::traits::eof(), stream.seek(1, std::ios_base::end));
    CHECK_EQUAL((concurrency::streams::istream::pos_type)content_len, stream.seek(content_len, std::ios_base::beg));
    CHECK_EQUAL((concurrency::streams::istream::pos_type)concurrency::streams::istream::traits::eof(), stream.seek(content_len + 1, std::ios_base::beg));
}
size_t seek_read_and_compare(concurrency::streams::istream stream, std::vector<uint8_t> buffer_to_compare, utility::size64_t offset, size_t count, size_t expected_read_count)
{
    std::vector<uint8_t> buffer;
    buffer.resize(count);
    stream.seek(offset);
    auto read_count = stream.streambuf().getn(buffer.data(), count).get();
    CHECK_EQUAL(expected_read_count, read_count);
    CHECK_ARRAY_EQUAL(buffer_to_compare.data() + offset, buffer.data(), (int)read_count);
    return read_count;
}