aboutsummaryrefslogtreecommitdiff
path: root/include/openvic-dataloader/detail
diff options
context:
space:
mode:
Diffstat (limited to 'include/openvic-dataloader/detail')
-rw-r--r--include/openvic-dataloader/detail/BasicParser.hpp37
-rw-r--r--include/openvic-dataloader/detail/CallbackOStream.hpp31
-rw-r--r--include/openvic-dataloader/detail/ClassExport.hpp9
-rw-r--r--include/openvic-dataloader/detail/Concepts.hpp21
-rw-r--r--include/openvic-dataloader/detail/LexyFwdDeclaration.hpp8
-rw-r--r--include/openvic-dataloader/detail/LexyReportError.hpp107
-rw-r--r--include/openvic-dataloader/detail/OStreamOutputIterator.hpp22
-rw-r--r--include/openvic-dataloader/detail/OptionalConstexpr.hpp9
-rw-r--r--include/openvic-dataloader/detail/utility/Concepts.hpp45
-rw-r--r--include/openvic-dataloader/detail/utility/Constexpr.hpp (renamed from include/openvic-dataloader/detail/VectorConstexpr.hpp)6
-rw-r--r--include/openvic-dataloader/detail/utility/ErrorRange.hpp11
-rw-r--r--include/openvic-dataloader/detail/utility/PointerHash.hpp (renamed from include/openvic-dataloader/detail/PointerHash.hpp)0
-rw-r--r--include/openvic-dataloader/detail/utility/SelfType.hpp (renamed from include/openvic-dataloader/detail/SelfType.hpp)0
-rw-r--r--include/openvic-dataloader/detail/utility/TypeName.hpp (renamed from include/openvic-dataloader/detail/TypeName.hpp)0
-rw-r--r--include/openvic-dataloader/detail/utility/Utility.hpp38
15 files changed, 256 insertions, 88 deletions
diff --git a/include/openvic-dataloader/detail/BasicParser.hpp b/include/openvic-dataloader/detail/BasicParser.hpp
deleted file mode 100644
index 7524bb5..0000000
--- a/include/openvic-dataloader/detail/BasicParser.hpp
+++ /dev/null
@@ -1,37 +0,0 @@
-#pragma once
-
-#include <string>
-#include <string_view>
-#include <vector>
-
-#include <openvic-dataloader/ParseError.hpp>
-#include <openvic-dataloader/ParseWarning.hpp>
-#include <openvic-dataloader/detail/Concepts.hpp>
-
-namespace ovdl::detail {
- class BasicParser {
- public:
- BasicParser();
-
- void set_error_log_to_null();
- void set_error_log_to_stderr();
- void set_error_log_to_stdout();
- void set_error_log_to(std::basic_ostream<char>& stream);
-
- bool has_error() const;
- bool has_fatal_error() const;
- bool has_warning() const;
-
- const std::vector<ParseError>& get_errors() const;
- const std::vector<ParseWarning>& get_warnings() const;
- std::string_view get_file_path() const;
-
- protected:
- std::vector<ParseError> _errors;
- std::vector<ParseWarning> _warnings;
-
- std::reference_wrapper<std::ostream> _error_stream;
- std::string _file_path;
- bool _has_fatal_error = false;
- };
-} \ No newline at end of file
diff --git a/include/openvic-dataloader/detail/CallbackOStream.hpp b/include/openvic-dataloader/detail/CallbackOStream.hpp
index 641d53f..f7cfc4a 100644
--- a/include/openvic-dataloader/detail/CallbackOStream.hpp
+++ b/include/openvic-dataloader/detail/CallbackOStream.hpp
@@ -6,10 +6,10 @@
#include <type_traits>
namespace ovdl::detail {
- template<typename Callback, class CHAR_T, class traits = std::char_traits<CHAR_T>>
- class BasicCallbackStreamBuffer : public std::basic_streambuf<CHAR_T, traits> {
+ template<typename Callback, class CharT, class traits = std::char_traits<CharT>>
+ class BasicCallbackStreamBuffer : public std::basic_streambuf<CharT, traits> {
public:
- using base_type = std::basic_streambuf<CHAR_T, traits>;
+ using base_type = std::basic_streambuf<CharT, traits>;
using callback_type = Callback;
using char_type = typename base_type::char_type;
using int_type = typename base_type::int_type;
@@ -29,11 +29,12 @@ namespace ovdl::detail {
};
int_type overflow(int_type ch) override {
+ auto c = static_cast<char_type>(ch);
if constexpr (std::is_same_v<void, typename decltype(std::function { _callback })::result_type>) {
- _callback(&ch, 1, _user_data);
+ _callback(&c, 1, _user_data);
return 1;
} else {
- return _callback(&ch, 1, _user_data); // returns the number of characters successfully written.
+ return _callback(&c, 1, _user_data); // returns the number of characters successfully written.
}
}
@@ -64,22 +65,28 @@ namespace ovdl::detail {
CallbackWStreamBuffer(Callback cb, void* user_data = nullptr) : base_type(cb, user_data) {}
};
- template<typename Callback, class CHAR_T, class traits = std::char_traits<CHAR_T>>
- class BasicCallbackStream : public std::basic_ostream<CHAR_T, traits> {
+ template<class CharT, typename Callback, class traits = std::char_traits<CharT>>
+ class BasicCallbackStream : public std::basic_ostream<CharT, traits> {
public:
- using base_type = std::basic_ostream<CHAR_T, traits>;
+ using base_type = std::basic_ostream<CharT, traits>;
BasicCallbackStream(Callback cb, void* user_data = nullptr)
: m_sbuf(cb, user_data),
- std::basic_ios<CHAR_T, traits>(&m_sbuf),
- std::basic_ostream<CHAR_T, traits>(&m_sbuf) {
- std::basic_ios<CHAR_T, traits>::init(&m_sbuf);
+ std::basic_ios<CharT, traits>(&m_sbuf),
+ std::basic_ostream<CharT, traits>(&m_sbuf) {
+ std::basic_ios<CharT, traits>::init(&m_sbuf);
}
private:
- BasicCallbackStreamBuffer<Callback, CHAR_T, traits> m_sbuf;
+ BasicCallbackStreamBuffer<Callback, CharT, traits> m_sbuf;
};
+ template<typename CharT>
+ auto make_callback_stream(auto&& cb, void* user_data = nullptr) {
+ using Callback = std::decay_t<decltype(cb)>;
+ return BasicCallbackStream<CharT, Callback> { std::forward<Callback>(cb), user_data };
+ }
+
template<typename Callback>
class CallbackStream : public BasicCallbackStream<Callback, char> {
public:
diff --git a/include/openvic-dataloader/detail/ClassExport.hpp b/include/openvic-dataloader/detail/ClassExport.hpp
deleted file mode 100644
index 27098ed..0000000
--- a/include/openvic-dataloader/detail/ClassExport.hpp
+++ /dev/null
@@ -1,9 +0,0 @@
-#pragma once
-
-#ifdef _MSC_VER
-#define OVDL_EXPORT __declspec(dllexport)
-#elif defined(__GNUC__)
-#define OVDL_EXPORT __attribute__((visibility("default")))
-#else
-#define OVDL_EXPORT
-#endif \ No newline at end of file
diff --git a/include/openvic-dataloader/detail/Concepts.hpp b/include/openvic-dataloader/detail/Concepts.hpp
deleted file mode 100644
index 3ca210c..0000000
--- a/include/openvic-dataloader/detail/Concepts.hpp
+++ /dev/null
@@ -1,21 +0,0 @@
-#pragma once
-
-#include <concepts>
-#include <optional>
-#include <utility>
-
-#include <openvic-dataloader/ParseError.hpp>
-
-namespace ovdl::detail {
- template<typename T, typename Self, typename... Args>
- concept LoadCallback =
- requires(T t, Self* self, Args... args) {
- { t(self, std::forward<Args>(args)...) } -> std::same_as<std::optional<ParseError>>;
- };
-
- template<typename T>
- concept Has_c_str =
- requires(T t) {
- { t.c_str() } -> std::same_as<const char*>;
- };
-} \ No newline at end of file
diff --git a/include/openvic-dataloader/detail/LexyFwdDeclaration.hpp b/include/openvic-dataloader/detail/LexyFwdDeclaration.hpp
new file mode 100644
index 0000000..554c88d
--- /dev/null
+++ b/include/openvic-dataloader/detail/LexyFwdDeclaration.hpp
@@ -0,0 +1,8 @@
+#pragma once
+
+namespace lexy {
+ struct default_encoding;
+
+ template<typename Encoding, typename MemoryResource>
+ struct buffer;
+} \ No newline at end of file
diff --git a/include/openvic-dataloader/detail/LexyReportError.hpp b/include/openvic-dataloader/detail/LexyReportError.hpp
new file mode 100644
index 0000000..3c32bd1
--- /dev/null
+++ b/include/openvic-dataloader/detail/LexyReportError.hpp
@@ -0,0 +1,107 @@
+#pragma once
+
+#include <cstddef>
+#include <sstream>
+#include <utility>
+#include <vector>
+
+#include <openvic-dataloader/ParseData.hpp>
+#include <openvic-dataloader/ParseError.hpp>
+
+#include <lexy/input_location.hpp>
+#include <lexy/visualize.hpp>
+
+#include "openvic-dataloader/detail/utility/Concepts.hpp"
+
+#include <lexy_ext/report_error.hpp>
+
+namespace ovdl::detail {
+ template<typename OutputIterator>
+ struct _ReportError {
+ OutputIterator _iter;
+ lexy::visualization_options _opts;
+ const char* _path;
+
+ struct _sink {
+ OutputIterator _iter;
+ lexy::visualization_options _opts;
+ const char* _path;
+ std::size_t _count;
+ std::vector<ParseError> _errors;
+
+ using return_type = std::vector<ParseError>;
+
+ template<typename Input, typename Reader, typename Tag>
+ void operator()(const lexy::error_context<Input>& context, const lexy::error<Reader, Tag>& error) {
+ _iter = lexy_ext::_detail::write_error(_iter, context, error, _opts, _path);
+ ++_count;
+
+ // Convert the context location and error location into line/column information.
+ auto context_location = lexy::get_input_location(context.input(), context.position());
+ auto location = lexy::get_input_location(context.input(), error.position(), context_location.anchor());
+
+ std::basic_stringstream<typename Reader::encoding::char_type> message;
+
+ // Write the main annotation.
+ if constexpr (std::is_same_v<Tag, lexy::expected_literal>) {
+ auto string = lexy::_detail::make_literal_lexeme<typename Reader::encoding>(error.string(), error.length());
+
+ message << "expected '" << string.data() << '\'';
+ } else if constexpr (std::is_same_v<Tag, lexy::expected_keyword>) {
+ auto string = lexy::_detail::make_literal_lexeme<typename Reader::encoding>(error.string(), error.length());
+
+ message << "expected keyword '" << string.data() << '\'';
+ } else if constexpr (std::is_same_v<Tag, lexy::expected_char_class>) {
+ message << "expected " << error.name();
+ } else {
+ message << error.message();
+ }
+
+ _errors.push_back(
+ ParseError {
+ ParseError::Type::Fatal, // TODO: distinguish recoverable errors from fatal errors
+ std::move(message.str()),
+ 0, // TODO: implement proper error codes
+ ParseData {
+ context.production(),
+ context_location.line_nr(),
+ context_location.column_nr(),
+ },
+ location.line_nr(),
+ location.column_nr(),
+ });
+ }
+
+ return_type finish() && {
+ if (_count != 0)
+ *_iter++ = '\n';
+ return _errors;
+ }
+ };
+ constexpr auto sink() const {
+ return _sink { _iter, _opts, _path, 0 };
+ }
+
+ /// Specifies a path that will be printed alongside the diagnostic.
+ constexpr _ReportError path(const char* path) const {
+ return { _iter, _opts, path };
+ }
+
+ constexpr _ReportError path(const detail::HasCstr auto& path_object) const {
+ return path(path_object.c_str());
+ }
+
+ /// Specifies an output iterator where the errors are written to.
+ template<typename OI>
+ constexpr _ReportError<OI> to(OI out) const {
+ return { out, _opts, _path };
+ }
+
+ /// Overrides visualization options.
+ constexpr _ReportError opts(lexy::visualization_options opts) const {
+ return { _iter, opts, _path };
+ }
+ };
+
+ constexpr auto ReporError = _ReportError<lexy::stderr_output_iterator> {};
+} \ No newline at end of file
diff --git a/include/openvic-dataloader/detail/OStreamOutputIterator.hpp b/include/openvic-dataloader/detail/OStreamOutputIterator.hpp
new file mode 100644
index 0000000..8f120c7
--- /dev/null
+++ b/include/openvic-dataloader/detail/OStreamOutputIterator.hpp
@@ -0,0 +1,22 @@
+#pragma once
+
+#include <memory>
+#include <ostream>
+
+namespace ovdl::detail {
+ struct OStreamOutputIterator {
+ std::reference_wrapper<std::ostream> _stream;
+
+ auto operator*() const noexcept {
+ return *this;
+ }
+ auto operator++(int) const noexcept {
+ return *this;
+ }
+
+ OStreamOutputIterator& operator=(char c) {
+ _stream.get().put(c);
+ return *this;
+ }
+ };
+} \ No newline at end of file
diff --git a/include/openvic-dataloader/detail/OptionalConstexpr.hpp b/include/openvic-dataloader/detail/OptionalConstexpr.hpp
deleted file mode 100644
index bcb12a7..0000000
--- a/include/openvic-dataloader/detail/OptionalConstexpr.hpp
+++ /dev/null
@@ -1,9 +0,0 @@
-#pragma once
-
-// THANK YOU APPLE FOR YOUR UTTER DISREGARD FOR C++20
-
-#if __cpp_lib_optional >= 202106L
-#define OVDL_OPTIONAL_CONSTEXPR constexpr
-#else
-#define OVDL_OPTIONAL_CONSTEXPR inline
-#endif \ No newline at end of file
diff --git a/include/openvic-dataloader/detail/utility/Concepts.hpp b/include/openvic-dataloader/detail/utility/Concepts.hpp
new file mode 100644
index 0000000..0ba91cc
--- /dev/null
+++ b/include/openvic-dataloader/detail/utility/Concepts.hpp
@@ -0,0 +1,45 @@
+#pragma once
+
+#include <concepts>
+#include <cstdint>
+#include <functional>
+#include <utility>
+
+namespace ovdl {
+ struct NodeLocation;
+ struct File;
+ namespace detail {
+ enum class buffer_error : std::uint8_t;
+ }
+}
+
+namespace ovdl::detail {
+ template<typename T, typename... Ts>
+ concept any_of = (std::same_as<T, Ts> || ...);
+
+ template<typename T>
+ concept HasCstr =
+ requires(T t) {
+ { t.c_str() } -> std::same_as<const char*>;
+ };
+
+ template<typename T>
+ concept HasPath = requires(T& t) {
+ { t.path() } -> std::same_as<const char*>;
+ };
+
+ template<typename T, typename Self, typename... Args>
+ concept LoadCallback =
+ requires(T&& t, Self&& self, Args&&... args) {
+ { std::invoke(std::forward<T>(t), std::forward<Self>(self), std::forward<Args>(args)...) } -> std::same_as<ovdl::detail::buffer_error>;
+ };
+
+ template<typename T>
+ concept IsEncoding = requires(T t) {
+ typename T::char_type;
+ typename T::int_type;
+ { T::template is_secondary_char_type<typename T::char_type>() } -> std::same_as<bool>;
+ { T::eof() } -> std::same_as<typename T::int_type>;
+ { T::to_int_type(typename T::char_type {}) } -> std::same_as<typename T::int_type>;
+ };
+} \ No newline at end of file
diff --git a/include/openvic-dataloader/detail/VectorConstexpr.hpp b/include/openvic-dataloader/detail/utility/Constexpr.hpp
index 7e7fa34..49479c5 100644
--- a/include/openvic-dataloader/detail/VectorConstexpr.hpp
+++ b/include/openvic-dataloader/detail/utility/Constexpr.hpp
@@ -2,6 +2,12 @@
// THANK YOU APPLE FOR YOUR UTTER DISREGARD FOR C++20
+#if __cpp_lib_optional >= 202106L
+#define OVDL_OPTIONAL_CONSTEXPR constexpr
+#else
+#define OVDL_OPTIONAL_CONSTEXPR inline
+#endif
+
#if __cpp_lib_constexpr_vector >= 201907L
#define OVDL_VECTOR_CONSTEXPR constexpr
#else
diff --git a/include/openvic-dataloader/detail/utility/ErrorRange.hpp b/include/openvic-dataloader/detail/utility/ErrorRange.hpp
new file mode 100644
index 0000000..a427f6c
--- /dev/null
+++ b/include/openvic-dataloader/detail/utility/ErrorRange.hpp
@@ -0,0 +1,11 @@
+#pragma once
+
+#include <utility>
+
+#include <openvic-dataloader/Error.hpp>
+
+#include <dryad/node.hpp>
+
+namespace ovdl::detail {
+ using error_range = decltype(std::declval<const error::Root*>()->errors());
+} \ No newline at end of file
diff --git a/include/openvic-dataloader/detail/PointerHash.hpp b/include/openvic-dataloader/detail/utility/PointerHash.hpp
index c0d28bc..c0d28bc 100644
--- a/include/openvic-dataloader/detail/PointerHash.hpp
+++ b/include/openvic-dataloader/detail/utility/PointerHash.hpp
diff --git a/include/openvic-dataloader/detail/SelfType.hpp b/include/openvic-dataloader/detail/utility/SelfType.hpp
index 5209700..5209700 100644
--- a/include/openvic-dataloader/detail/SelfType.hpp
+++ b/include/openvic-dataloader/detail/utility/SelfType.hpp
diff --git a/include/openvic-dataloader/detail/TypeName.hpp b/include/openvic-dataloader/detail/utility/TypeName.hpp
index 1a34a0f..1a34a0f 100644
--- a/include/openvic-dataloader/detail/TypeName.hpp
+++ b/include/openvic-dataloader/detail/utility/TypeName.hpp
diff --git a/include/openvic-dataloader/detail/utility/Utility.hpp b/include/openvic-dataloader/detail/utility/Utility.hpp
new file mode 100644
index 0000000..138a029
--- /dev/null
+++ b/include/openvic-dataloader/detail/utility/Utility.hpp
@@ -0,0 +1,38 @@
+#pragma once
+
+#include <string_view>
+#include <type_traits>
+
+#include "openvic-dataloader/detail/utility/TypeName.hpp"
+
+namespace ovdl::detail {
+ [[noreturn]] inline void unreachable() {
+ // Uses compiler specific extensions if possible.
+ // Even if no extension is used, undefined behavior is still raised by
+ // an empty function body and the noreturn attribute.
+#ifdef __GNUC__ // GCC, Clang, ICC
+ __builtin_unreachable();
+#elif defined(_MSC_VER) // MSVC
+ __assume(false);
+#endif
+ }
+
+ template<typename Kind>
+ constexpr std::string_view get_kind_name() {
+ constexpr auto name = type_name<Kind>();
+
+ return name;
+ }
+
+ template<typename EnumT>
+ requires std::is_enum_v<EnumT>
+ constexpr std::underlying_type_t<EnumT> to_underlying(EnumT e) {
+ return static_cast<std::underlying_type_t<EnumT>>(e);
+ }
+
+ template<typename EnumT>
+ requires std::is_enum_v<EnumT>
+ constexpr EnumT from_underlying(std::underlying_type_t<EnumT> ut) {
+ return static_cast<EnumT>(ut);
+ }
+} \ No newline at end of file