1#ifndef RDS2CPP_PARSE_RDA_HPP
2#define RDS2CPP_PARSE_RDA_HPP
9#include "utils_parse.hpp"
10#include "SharedParseInfo.hpp"
11#include "parse_pairlist.hpp"
50template<
class Reader_>
52 std::unique_ptr<byteme::BufferedReader<unsigned char> > srcptr;
64 std::string header(5,
'\0');
65 quick_extract(src, 5,
reinterpret_cast<unsigned char*
>(header.data()));
66 if (header !=
"RDX2\n" && header !=
"RDX3\n") {
67 throw std::runtime_error(
"only RDX2 or RDX3 formats are currently supported");
71 quick_extract(src, 2,
reinterpret_cast<unsigned char*
>(header.data()));
72 if (header !=
"X\n") {
73 throw std::runtime_error(
"only RDA files in XDR format are currently supported");
75 }
catch (std::exception& e) {
76 throw traceback(
"failed to read the header from the RDA preamble", e);
82 }
catch (std::exception& e) {
83 throw traceback(
"failed to read the format version number from the RDA preamble", e);
88 }
catch (std::exception& e) {
89 throw traceback(
"failed to read the writer version number from the RDA preamble", e);
94 }
catch (std::exception& e) {
95 throw traceback(
"failed to read the reader version number from the RDA preamble", e);
101 std::int32_t encoding_length = 0;
103 encoding_length = quick_integer<I<
decltype(encoding_length)> >(src);
104 if (encoding_length < 0) {
105 throw std::runtime_error(
"encoding length should be non-negative");
107 }
catch (std::exception& e) {
108 throw traceback(
"failed to read the encoding length from the RDA preamble", e);
113 quick_extract(src, encoding_length,
reinterpret_cast<unsigned char*
>(encoding.data()));
114 output.
encoding = string_encoding_from_name(encoding);
115 }
catch (std::exception& e) {
116 throw traceback(
"failed to read the encoding string from the RDA preamble", e);
121 SharedParseInfo shared;
123 auto details = parse_header(src);
124 auto sexp_type = details[3];
125 if (sexp_type !=
static_cast<unsigned char>(SEXPType::LIST)) {
126 throw std::runtime_error(
"expected RDA file to contain a pairlist");
129 auto payload = parse_pairlist_body(src, details, shared);
130 output.
objects.reserve(payload->data.size());
131 for (
auto& x : payload->data) {
132 if (!x.tag.has_value()) {
133 throw std::runtime_error(
"expected RDA file to contain a tagged pairlist");
135 output.
objects.emplace_back(std::move(*(x.tag)), std::move(x.value));
139 output.
symbols = std::move(shared.symbols);
Information about an RDA file.
Parse an RDS file in C++.
Definition StringEncoding.hpp:12
RdaFile parse_rda(Reader_ &reader, const ParseRdaOptions &options)
Definition parse_rda.hpp:51
Container_ create(Value_ x, Args_ &&... args)
constexpr Dest_ cap(Value_ x)
Options for parse_rda().
Definition parse_rda.hpp:27
std::size_t buffer_size
Definition parse_rda.hpp:37
bool parallel
Definition parse_rda.hpp:31
Contents of the parsed RDA file.
Definition RdaFile.hpp:47
std::vector< RdaObject > objects
Definition RdaFile.hpp:71
std::vector< Symbol > symbols
Definition RdaFile.hpp:83
StringEncoding encoding
Definition RdaFile.hpp:66
std::vector< ExternalPointer > external_pointers
Definition RdaFile.hpp:89
std::vector< Environment > environments
Definition RdaFile.hpp:77
Version writer_version
Definition RdaFile.hpp:56
Version reader_version
Definition RdaFile.hpp:61
std::int32_t format_version
Definition RdaFile.hpp:51