mirror of
https://github.com/NixOS/nix
synced 2025-06-29 02:11:15 +02:00
sinkToSource: avoid heap allocation
This commit is contained in:
parent
06123f6284
commit
4f8f12f79a
1 changed files with 19 additions and 16 deletions
|
@ -227,8 +227,7 @@ std::unique_ptr<FinishSink> sourceToSink(std::function<void(Source &)> fun)
|
||||||
throw EndOfFile("coroutine has finished");
|
throw EndOfFile("coroutine has finished");
|
||||||
}
|
}
|
||||||
|
|
||||||
size_t n = std::min(cur.size(), out_len);
|
size_t n = cur.copy(out, out_len);
|
||||||
memcpy(out, cur.data(), n);
|
|
||||||
cur.remove_prefix(n);
|
cur.remove_prefix(n);
|
||||||
return n;
|
return n;
|
||||||
});
|
});
|
||||||
|
@ -260,7 +259,7 @@ std::unique_ptr<Source> sinkToSource(
|
||||||
{
|
{
|
||||||
struct SinkToSource : Source
|
struct SinkToSource : Source
|
||||||
{
|
{
|
||||||
typedef boost::coroutines2::coroutine<std::string> coro_t;
|
typedef boost::coroutines2::coroutine<std::string_view> coro_t;
|
||||||
|
|
||||||
std::function<void(Sink &)> fun;
|
std::function<void(Sink &)> fun;
|
||||||
std::function<void()> eof;
|
std::function<void()> eof;
|
||||||
|
@ -271,33 +270,37 @@ std::unique_ptr<Source> sinkToSource(
|
||||||
{
|
{
|
||||||
}
|
}
|
||||||
|
|
||||||
std::string cur;
|
std::string_view cur;
|
||||||
size_t pos = 0;
|
|
||||||
|
|
||||||
size_t read(char * data, size_t len) override
|
size_t read(char * data, size_t len) override
|
||||||
{
|
{
|
||||||
if (!coro) {
|
bool hasCoro = coro.has_value();
|
||||||
|
if (!hasCoro) {
|
||||||
coro = coro_t::pull_type([&](coro_t::push_type & yield) {
|
coro = coro_t::pull_type([&](coro_t::push_type & yield) {
|
||||||
LambdaSink sink([&](std::string_view data) {
|
LambdaSink sink([&](std::string_view data) {
|
||||||
if (!data.empty()) yield(std::string(data));
|
if (!data.empty()) {
|
||||||
|
yield(data);
|
||||||
|
}
|
||||||
});
|
});
|
||||||
fun(sink);
|
fun(sink);
|
||||||
});
|
});
|
||||||
}
|
}
|
||||||
|
|
||||||
if (!*coro) { eof(); unreachable(); }
|
if (cur.empty()) {
|
||||||
|
if (hasCoro) {
|
||||||
if (pos == cur.size()) {
|
|
||||||
if (!cur.empty()) {
|
|
||||||
(*coro)();
|
(*coro)();
|
||||||
}
|
}
|
||||||
cur = coro->get();
|
if (*coro) {
|
||||||
pos = 0;
|
cur = coro->get();
|
||||||
|
} else {
|
||||||
|
coro.reset();
|
||||||
|
eof();
|
||||||
|
unreachable();
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
auto n = std::min(cur.size() - pos, len);
|
size_t n = cur.copy(data, len);
|
||||||
memcpy(data, cur.data() + pos, n);
|
cur.remove_prefix(n);
|
||||||
pos += n;
|
|
||||||
|
|
||||||
return n;
|
return n;
|
||||||
}
|
}
|
||||||
|
|
Loading…
Add table
Add a link
Reference in a new issue