PLCnext API Documentation 25.0.2.69
RscWriteEnumerator.hxx
1
2//
3// Copyright Phoenix Contact GmbH & Co. KG
4//
6#pragma once
8#include "Arp/Base/Rsc/Commons/Rsc.hpp"
9#include "Arp/Base/Rsc/Commons/RscArrayWriter.hpp"
10#include "Arp/Base/Rsc/Commons/IRscWriteEnumerator.hxx"
11#include "Arp/Base/Rsc/Commons/Services/RscWriter.hpp"
12#include "Arp/Base/Commons/Exceptions/InvalidOperationException.hpp"
13
14namespace Arp::Base::Rsc::Commons::Services
15{
16
18template<class T>
20{
21public: // construction
22 RscWriteEnumerator(RscWriter& rscWriter, bool isArrayEnumerator);
23
24 // canonical construction/destruction/assignment
25 RscWriteEnumerator(const RscWriteEnumerator& arg) = delete;
27 RscWriteEnumerator& operator=(const RscWriteEnumerator& arg) = delete;
29 ~RscWriteEnumerator(void)noexcept;
30
31public: // operations of IRscWriteEnumerator
32 void BeginWrite(size_t currentArrayLength = (size_t) -1)override;
33 void WriteNext(const T& current)override;
34 RscArrayWriter WriteNext(size_t arraySize, RscType arrayElementType)override;
35 void EndWrite(void)override;
36
37private: // fields
38 RscWriter& rscWriter;
39 bool isArrayEnumerator = false;
40 size_t arrayLength = 0;
41 bool ended = false;
42 RscType rscType = RscTypeDeduction().Get<T>();
43 size_t fieldCount = 0;
44 bool isConcreteType = RscTypeInfo::IsConcreteType(this->rscType);
45};
46
48// inline methods of class RscEnumerator
49
53template<class T>
55
60template<class T>
62
65template<class T>
66inline RscWriteEnumerator<T>::~RscWriteEnumerator()noexcept = default;
67
72template<class T>
73inline RscWriteEnumerator<T>::RscWriteEnumerator(RscWriter& rscWriter, bool isArrayEnumerator)
74 : isArrayEnumerator(isArrayEnumerator)
75 , rscWriter(rscWriter)
76 , rscType(RscTypeDeduction::GetFrom(T()))
77 , fieldCount(StructInfo<T>().FieldCount)
78{
79}
80
84template<class T>
85inline void RscWriteEnumerator<T>::BeginWrite(size_t currentArrayLength)
86{
87 this->arrayLength = currentArrayLength;
88
89 if(this->isArrayEnumerator)
90 {
91 if(this->arrayLength == (size_t) -1)
92 {
93 throw ArgumentException("Array length has to be defined for array enumerators.");
94 }
95 this->rscWriter.WriteTag(RscType::Array);
96 // Write element Tag
97 if(this->rscType == RscType::Struct)
98 {
99 this->rscWriter.WriteStructInfo(this->fieldCount);
100 }
101 else
102 {
103 this->rscWriter.WriteTag(this->rscType);
104 }
105 this->rscWriter.WriteArrayLength(this->arrayLength);
106 }
107 else // standard enumerator
108 {
109 if(this->arrayLength != (size_t) -1)
110 {
111 throw ArgumentException("Array length could not be defined for standard enumerators.");
112 }
113 this->rscWriter.WriteTag(RscType::Enumerator);
114 }
115}
116
120template<class T>
121inline void RscWriteEnumerator<T>::WriteNext(const T& current)
122{
123 if(this->isArrayEnumerator)
124 {
125 if(this->arrayLength == 0)
126 {
127 throw InvalidOperationException("End of array enumerator reached");
128 }
129 // else
130 --this->arrayLength;
131 this->rscWriter.Write(current, this->isConcreteType);
132 }
133 else // use standard enumerator
134 {
135 this->rscWriter.WriteEnumeratorTag(this->rscType);
136 if(this->rscType == RscType::Struct)
137 {
138 this->rscWriter.WriteFieldCount(this->fieldCount);
139 }
140 this->rscWriter.Write(current, true);
141 }
142}
143
149template<class T>
150inline RscArrayWriter RscWriteEnumerator<T>::WriteNext(size_t arraySize, RscType arrayElementType)
151{
152 this->rscWriter.WriteTag(RscType::Array);
153 this->rscWriter.WriteTag(arrayElementType);
154 this->rscWriter.WriteArrayLength(arraySize);
155 return RscArrayWriter(arraySize, arrayElementType, this->rscWriter);
156}
157
163template<class T>
165{
166 if(this->isArrayEnumerator)
167 {
168 if(this->arrayLength != 0)
169 {
170 throw InvalidOperationException("End of array enumerator was not reached yet");
171 }
172 }
173 else // standard enumeration was written
174 {
175 this->rscWriter.WriteEnumeratorTag(RscType::End);
176 }
177 this->ended = true;
178}
179
180} // end of namespace Arp::Base::Rsc::Commons::Services
This exception is thrown when an invalid argument occurs.
Definition: ArgumentException.hpp:17
This exception is thrown when an operation cannot be executed because the related state is invalid.
Definition: InvalidOperationException.hpp:16
Interface for writing an array enumeration or enumeration of unspefied length.
Definition: IRscWriteEnumerator.hxx:20
Helper class to write a dynamic array of primtive types from RscVariant. This class uses the array in...
Definition: RscArrayWriter.hpp:23
This class is used to deduct RSC types automatically by compilation.
Definition: RscTypeDeduction.hpp:24
constexpr RscType Get(void)
Gets the RscType of the as argument passed template parameter.
Definition: RscTypeDeduction.hpp:47
static bool IsConcreteType(RscType type)
Determines if the supplied type specifies a concrete type, i.e not unspecified and not object.
Definition: RscTypeInfo.cpp:242
Implementation of IRscWriteEnumerator used on client side.
Definition: RscWriteEnumerator.hxx:20
void WriteNext(const T &current) override
Writes the next value of the enumeration.
Definition: RscWriteEnumerator.hxx:121
void BeginWrite(size_t currentArrayLength=(size_t) -1) override
This operation is called at the begin of writing the enumeration.
Definition: RscWriteEnumerator.hxx:85
RscWriteEnumerator(RscWriter &rscWriter, bool isArrayEnumerator)
Constructs an RscEnumeratorBase instance.
Definition: RscWriteEnumerator.hxx:73
void EndWrite(void) override
This operation has to be called when the enumerating has finished.
Definition: RscWriteEnumerator.hxx:164
RscWriteEnumerator(RscWriteEnumerator &&arg) noexcept
The default move constructor.
~RscWriteEnumerator(void) noexcept
Destructs this instance and checks if the enumerations has ended.
RscWriteEnumerator & operator=(RscWriteEnumerator &&arg) noexcept
The default move-assignment operator.
Writes marshalled data of RSC services.
Definition: RscWriter.hpp:34
void WriteFieldCount(size_t fieldCount)
Writes the field count of a struct to RSC.
Definition: RscWriter.cpp:132
void WriteTag(RscType tag)
Writes a data tag to RSC.
Definition: RscWriter.cpp:125
void WriteArrayLength(size_t arraySize)
Writes the length of an array to RSC.
Definition: RscWriter.cpp:139
void WriteEnumeratorTag(RscType tag)
Writes an enumerator tag to RSC.
Definition: RscWriter.cpp:153
void Write(const RscPtr &value, bool omitTag=false)
Writes a value to RSC.
Definition: RscWriter.cpp:78
void WriteStructInfo(size_t fieldCount)
Writes the struct info to RSC.
Definition: RscWriter.cpp:146
This class provides the number of fields of a concrete struct. This class is specialized for concrete...
Definition: StructInfo.hxx:26