72 auto rd32 = [](
const char* p) { std::int32_t v; std::memcpy(&v, p, 4);
return v; };
74 std::size_t p = 0, prev = 0;
76 while (p + 8 <= buf.size()) {
77 const std::int32_t reclen = rd32(&buf[p]);
78 if (reclen < 0 || p + 8 +
static_cast<std::size_t
>(reclen) > buf.size())
break;
80 if (reclen == 24 && std::memcmp(&buf[p + 4],
"restart ", 8) == 0) {
82 const std::size_t start = prev;
83 const bool complete = (rd32(&buf[p + 4 + 8]) & 16) != 0;
88 if (want >= 0 && rd32(&buf[p + 4 + 16]) == want && !L.
have_target) {
93 p += 8 +
static_cast<std::size_t
>(reclen);
117 std::vector<char> out;
119 out.insert(out.end(), buf.begin(), buf.begin() + L.
header_end);
120 out.insert(out.end(), buf.begin() + L.
base, buf.begin() + L.
base_end);
137 std::vector<char> out;
139 out.insert(out.end(), buf.begin(), buf.begin() + L.
header_end);
150inline std::vector<char>
splice_base(
const std::vector<char>& hdr_base,
151 const std::vector<char>& body)
155 std::vector<char> out;
156 out.reserve(hdr_base.size() + (body.size() - B.
header_end));
157 out.insert(out.end(), hdr_base.begin(), hdr_base.end());
158 out.insert(out.end(), body.begin() + B.
header_end, body.end());
175 const bool target_is_base = (L.
target == L.
base);
176 std::vector<char> out;
179 out.insert(out.end(), buf.begin(), buf.begin() + L.
header_end);
180 out.insert(out.end(), buf.begin() + L.
base, buf.begin() + L.
base_end);
RestartLayout scan_restart(const std::vector< char > &buf, std::int32_t want)
Walk the record chain and locate the header, the base dump and the target dump.
std::vector< char > extract_restart_record(const std::vector< char > &buf, std::int32_t want)
[header][complete base][target]: self-contained, no cache needed.
std::vector< char > splice_base(const std::vector< char > &hdr_base, const std::vector< char > &body)
Put the cached base back in front of a base-less transfer.
std::vector< char > extract_record_no_base(const std::vector< char > &buf, std::int32_t want)
[header][target], the wire payload with the base omitted.
std::vector< char > extract_header_and_base(const std::vector< char > &buf)
[header][complete base], the run-wide constant that is cached per rank and published as <project>/res...
bool has_complete_restart(const std::vector< char > &buf)
Does this buffer contain a complete restart dump (the base)?
Byte offsets of the structural landmarks in a restart buffer. An offset is meaningful only when its h...
std::size_t base
start of the first COMPLETE restart dump
std::size_t base_end
one past it (start of the next dump, or the buffer size)
bool have_header
at least one dump was found
bool have_base
a complete restart dump was found
std::size_t target
start of the first dump whose ncount equals want
bool have_target
a dump with ncount == want was found
std::size_t header_end
end of header + plot-id block = start of first dump
std::size_t target_end
one past it (start of the next dump, or the buffer size)