summaryrefslogtreecommitdiff
path: root/src/codec
diff options
context:
space:
mode:
Diffstat (limited to 'src/codec')
-rw-r--r--src/codec/data.h14
-rw-r--r--src/codec/simple.h81
2 files changed, 93 insertions, 2 deletions
diff --git a/src/codec/data.h b/src/codec/data.h
index 9eb2bfc..397aed1 100644
--- a/src/codec/data.h
+++ b/src/codec/data.h
@@ -91,12 +91,22 @@ public:
SAW_DEFAULT_MOVE(data);
template<string_literal lit>
+ void set(data<typename parameter_pack_type<parameter_key_pack_index<lit, literals...>::value, T...>::type, encode::Native> val){
+ value_ = std::move(val);
+ }
+
+ template<string_literal lit>
bool holds_alternative() const {
- return std::holds_alternative<parameter_key_pack_index<lit, literals...>::value>(value_);
+ return (parameter_key_pack_index<lit, literals...>::value == value_.index());
}
template<string_literal lit>
- data<typename parameter_pack_type<parameter_key_pack_index<lit, literals...>::value>::type, encode::Native>& get(){
+ data<typename parameter_pack_type<parameter_key_pack_index<lit, literals...>::value, T...>::type, encode::Native>& get(){
+ return std::get<parameter_key_pack_index<lit, literals...>::value>(value_);
+ }
+
+ template<string_literal lit>
+ const data<typename parameter_pack_type<parameter_key_pack_index<lit, literals...>::value, T...>::type, encode::Native>& get() const{
return std::get<parameter_key_pack_index<lit, literals...>::value>(value_);
}
};
diff --git a/src/codec/simple.h b/src/codec/simple.h
index 8712c6d..8760754 100644
--- a/src/codec/simple.h
+++ b/src/codec/simple.h
@@ -82,6 +82,9 @@ struct kelsimple_encode<schema::Struct<schema::Member<T,Lits>...>,FromEnc> {
constexpr string_literal Literal = parameter_key_pack_type<i, Lits...>::literal;
{
auto eov = kelsimple_encode<Type, FromEnc>::encode(from.template get<Literal>(), to);
+ if(eov.is_error()){
+ return eov;
+ }
}
if constexpr ((i+1) < sizeof...(T)){
auto eov = encode_member<i+1>(from, to);
@@ -97,6 +100,41 @@ struct kelsimple_encode<schema::Struct<schema::Member<T,Lits>...>,FromEnc> {
}
};
+template<typename... T, string_literal... Lits, typename FromEnc>
+struct kelsimple_encode<schema::Union<schema::Member<T,Lits>...>,FromEnc> {
+ template<std::size_t i>
+ static error_or<void> encode_member(const data<schema::Union<schema::Member<T,Lits>...>, FromEnc>& from, buffer& to){
+ using Type = typename parameter_pack_type<i,T...>::type;
+ constexpr string_literal Literal = parameter_key_pack_type<i, Lits...>::literal;
+ if (from.template holds_alternative<Literal>()) {
+ {
+ auto eov = stream_value<schema::UInt64>::encode(static_cast<uint64_t>(i), to);
+ if(eov.is_error()){
+ return eov;
+ }
+ }
+ {
+ auto eov = kelsimple_encode<Type, FromEnc>::encode(from.template get<Literal>(), to);
+ if(eov.is_error()){
+ return eov;
+ }
+ }
+ }
+
+ if constexpr ( (i+1) < sizeof...(T) ){
+ auto eov = encode_member<i+1>(from, to);
+ if(eov.is_error()){
+ return eov;
+ }
+ }
+ return void_t{};
+ }
+
+ static error_or<void> encode(const data<schema::Union<schema::Member<T,Lits>...>, FromEnc>& from, buffer& to){
+ return encode_member<0>(from, to);
+ }
+};
+
template<typename... T, typename FromEnc>
struct kelsimple_encode<schema::Tuple<T...>, FromEnc> {
template<std::size_t i>
@@ -207,6 +245,9 @@ struct kelsimple_decode<schema::Struct<schema::Member<T,Lits>...>,FromEnc> {
constexpr string_literal Literal = parameter_key_pack_type<i, Lits...>::literal;
{
auto eov = kelsimple_decode<Type, FromEnc>::decode(from, to.template get<Literal>());
+ if(eov.is_error()){
+ return eov;
+ }
}
if constexpr ((i+1) < sizeof...(T)){
auto eov = decode_member<i+1>(from, to);
@@ -222,6 +263,46 @@ struct kelsimple_decode<schema::Struct<schema::Member<T,Lits>...>,FromEnc> {
}
};
+
+template<typename... T, string_literal... Lits, typename FromEnc>
+struct kelsimple_decode<schema::Union<schema::Member<T,Lits>...>,FromEnc> {
+ template<uint64_t i>
+ static error_or<void> decode_member(buffer& from, data<schema::Union<schema::Member<T,Lits>...>, FromEnc>& to, uint64_t val){
+ using Type = typename parameter_pack_type<i,T...>::type;
+ constexpr string_literal Literal = parameter_key_pack_type<i, Lits...>::literal;
+
+ if( i == val ){
+ to.template set<Literal>(data<Type, FromEnc>{});
+ auto eov = kelsimple_decode<Type, FromEnc>::decode(from, to.template get<Literal>());
+ if(eov.is_error()){
+ return eov;
+ }
+ return void_t{};
+ }
+
+ if constexpr ((i+1) < sizeof...(T)){
+ auto eov = decode_member<i+1>(from, to, val);
+ if(eov.is_error()){
+ return eov;
+ }
+ }
+ return void_t{};
+
+ }
+ static error_or<void> decode(buffer& from, data<schema::Union<schema::Member<T,Lits>...>, FromEnc>& to){
+ uint64_t val{};
+ auto eov = stream_value<schema::UInt64>::decode(val, from);
+ if(eov.is_error()){
+ return eov;
+ }
+ if ( val >= sizeof...(T) ){
+ return make_error<err::invalid_state>();
+ }
+ return decode_member<0>(from, to, val);
+ }
+
+};
+
template<typename... T, typename FromEnc>
struct kelsimple_decode<schema::Tuple<T...>,FromEnc> {
template<std::size_t i>