PLCnext API Documentation  22.9.0.33
RscArrayWriter.hpp
1 //
3 // Copyright PHOENIX CONTACT Electronics GmbH
4 //
6 #pragma once
7 #include "Arp/System/Core/Arp.h"
8 #include "Arp/System/Rsc/Services/Rsc.h"
9 #include "Arp/System/Commons/Exceptions/Exceptions.h"
10 #include "Arp/System/Rsc/Services/RemotingWriter.hpp"
11 #include "Arp/System/Rsc/Services/RscVariant.hxx"
12 #include <functional>
13 
14 namespace Arp { namespace System { namespace Rsc { namespace Services
15 {
16 
22 {
23 public: // typedefs
24  using WriteElementFunction = RscVariant<>::WriteElementFunction;
25 
26 public: // construction/destruction
30  template<int N>
31  RscArrayWriter(const RscVariant<N>& value);
33  RscArrayWriter(size_t size, RscType elementType, WriteElementFunction writeFunction);
35  RscArrayWriter(size_t size, RscType elementType, RemotingWriter& writer, size_t dimensions = 1);
37  RscArrayWriter(const RscArrayWriter& arg) = default;
39  RscArrayWriter& operator=(const RscArrayWriter& arg) = default;
41  ~RscArrayWriter(void) = default;
42 
43 public: // setter/getter operations
48  size_t GetSize(void)const;
49 
54  RscType GetElementType(void)const;
55 
60  size_t GetPosition(void)const;
61 
62 public: // operations
69  template<class T>
70  void WriteNext(const T& current);
71 
77  template<int N>
78  void WriteNext(const RscString<N>& current);
79 
80  template<int N>
81  void WriteNext(const RscVariant<N>& current);
82 
88  void WriteNext(const byte* pCurrent);
89 
96 
97  template<int MaxStringSize> RscVariant<MaxStringSize> WriteNextStruct();
98 
99 
100 private: // methods
101  void WriteRemotingValue(RscType type, const byte* pValue);
102 
103 private: // fields
104  RscArrayInformation arrayInformation;
105  size_t position = 0;
106  RemotingWriter* pWriter = nullptr;
107  WriteElementFunction writeElementFunction;
108  size_t maxStringSize = 0;
109 };
110 
112 // inline methods of class RscArrayWriter<T>
113 
114 template<int N>
116  : arrayInformation(value.GetArrayInformation())
117  , pWriter(value.typeInfo.pWriter)
118  , maxStringSize(N)
119 {
120  if (this->GetElementType() == RscType::None)
121  {
122  throw ArgumentException::Create("arrayElementType", this->GetElementType());
123  }
124 
125  if(this->arrayInformation.Dimensions == 0)
126  {
127  throw ArgumentException("{0}: dimension size has to be >= 0", __FUNCTION__);
128  }
129 
130  if (value.typeInfo.pWriteElementFunction != nullptr)
131  {
132  this->writeElementFunction = *value.typeInfo.pWriteElementFunction;
133  }
134  else if(this->pWriter != nullptr)
135  {
136  this->writeElementFunction = [&](RscType type, const byte * pValue)
137  {
138  WriteRemotingValue(type, pValue);
139  };
140  }
141  else
142  {
143  throw ArgumentException("WriteElementFunction in RscVariant has to be defined");
144  }
145 }
146 
147 
148 inline size_t RscArrayWriter::GetSize()const
149 {
150  return this->arrayInformation.Size;
151 }
152 
154 {
155  return this->arrayInformation.ElementType;
156 }
157 
158 inline size_t RscArrayWriter::GetPosition()const
159 {
160  return this->position;
161 }
162 
163 template<class T>
164 inline void RscArrayWriter::WriteNext(const T& current)
165 {
166  if(!IsPrimitiveRscType(this->GetElementType()))
167  {
168  throw InvalidOperationException("This method can only be used with primitve Types");
169  }
170  this->WriteNext(reinterpret_cast<const byte*>(&current));
171 }
172 
173 template<>
174 inline void RscArrayWriter::WriteNext(const DateTime& current)
175 {
176  if(this->GetElementType() != RscType::DateTime)
177  {
178  throw InvalidOperationException("This method can only be used for array of DateTime");
179  }
180  this->WriteNext(reinterpret_cast<const byte*>(&current));
181 }
182 
183 template<int N>
184 inline void RscArrayWriter::WriteNext(const RscString<N>& current)
185 {
186  if(this->GetElementType() != RscType::Utf8String)
187  {
188  throw InvalidOperationException("This instance of RscArrayWriter is not initialized for string operations");
189  }
190  if(N != this->maxStringSize)
191  {
192  throw InvalidOperationException("Size of current doesn't fit to maxStringSize");
193  }
194  this->writeElementFunction(this->GetElementType(), reinterpret_cast<const byte*>(current.CStr()));
195  ++this->position;
196 }
197 
198 template<int MaxStringSize>
199 inline RscVariant<MaxStringSize> RscArrayWriter::WriteNextStruct()
200 {
201 
202  if(this->arrayInformation.ElementType != RscType::Struct)
203  {
204  throw InvalidOperationException("This method is only valid with struct element types");
205  }
206 
207  RscVariant<MaxStringSize> structVariant;
208 
209  if(this->pWriter == nullptr)
210  {
211  structVariant = RscVariant<MaxStringSize>::CreateStructVariant(this->arrayInformation.FieldCount);
212  structVariant.SetWriteElementFunction(&this->writeElementFunction);
213  this->writeElementFunction(RscType::Struct, structVariant.GetDataAddress());
214  }
215  else
216  {
217  structVariant = RscVariant<MaxStringSize>::CreateStructVariant(this->arrayInformation.FieldCount, *this->pWriter);
218  }
219 
220  ++this->position;
221  return structVariant;
222 }
223 
224 template<int N>
225 inline void RscArrayWriter::WriteNext(const RscVariant<N>& current)
226 {
227  if(this->GetElementType() != RscType::Object)
228  {
229  throw InvalidOperationException("This instance of RscArrayWriter is not initialized to contain objects");
230  }
231  if(N != this->maxStringSize)
232  {
233  throw InvalidOperationException("Size of current doesn't fit to maxStringSize");
234  }
235  this->writeElementFunction(current.GetType(), current.GetDataAddress());
236  if(current.ContainsTypeInformation())
237  {
238  current.typeInfo.pWriter = this->pWriter;
239  }
240  ++this->position;
241 }
242 
243 }}}} // end of namespace Arp::System::Rsc::Services
The class contains date and time informations.
Definition: DateTime.hpp:45
This exception is used when an invalid argument occurs.
Definition: ArgumentException.hpp:15
static ArgumentException Create(const char *paramName, const T &paramValue)
Creates an ArgumentException instance using a default message text.
Definition: ArgumentException.hpp:112
This exception is used when a method call is invalid for object's current state.
Definition: InvalidOperationException.hpp:15
Helper class to read an array of primtive types from an RscVariant. This class uses the array informa...
Definition: RscArrayWriter.hpp:22
RscArrayWriter & operator=(const RscArrayWriter &arg)=default
Assignment operator.
~RscArrayWriter(void)=default
Destructs this instance and frees all resources.
RscArrayWriter WriteNextArray(size_t size)
Writes the next subarray for arrays with more than one dimension. The next subarray is written with a...
RscArrayWriter(const RscVariant< N > &value)
Constructs an RscArray instance.
Definition: RscArrayWriter.hpp:115
RscArrayWriter(const RscArrayWriter &arg)=default
Copy constructor.
RscType GetElementType(void) const
Returns the element type
Definition: RscArrayWriter.hpp:153
size_t GetSize(void) const
Returns number of Elements contained in array
Definition: RscArrayWriter.hpp:148
size_t GetPosition(void) const
Returns current writing position in array
Definition: RscArrayWriter.hpp:158
RscArrayWriter(size_t size, RscType elementType, RemotingWriter &writer, size_t dimensions=1)
Constructs an RscArrayWriter instance.
void WriteNext(const T &current)
Writes the next single array element using the callback function given by ArrayInformation of RscVari...
Definition: RscArrayWriter.hpp:164
void WriteNext(const byte *pCurrent)
Writes the next single array element using the callback function given by ArrayInformation of RscVari...
RscArrayWriter(size_t size, RscType elementType, WriteElementFunction writeFunction)
Constructs an RscArrayWriter instance.
Contains a static string with string lentgh up to N characters. The string has to be null terminated.
Definition: RscString.hxx:21
const char * CStr(void) const
Returns pointer to internal buffer.
Definition: RscString.hxx:111
Rsc container class for primitive data type, strings or information about arrays or structs....
Definition: RscVariant.hxx:39
static RscVariant< MaxStringSize > CreateStructVariant(size_t fieldCount)
Creates a new RscVariant initialized with RscStructInformation
Definition: RscVariant.hxx:557
void SetWriteElementFunction(WriteElementFunction *pFunction) const
Sets callback for write function to write a single array element. This could only be used for Variant...
Definition: RscVariant.hxx:724
const byte * GetDataAddress(void) const
Gets a raw pointer to internal data buffer. To read data prefer CopyTo and to write prefer assignment...
Definition: RscVariant.hxx:514
@ System
System components used by the System, Device, Plc or Io domains.
RscType
Datatypes supported by Rsc. Values are identical with CommonRemoting::RemotingMarshalType....
Definition: RscType.hpp:37
@ Object
Object type handled by Rsc as RscVariant
@ Struct
Complex datatype with implements IRscSerializable
@ DateTime
Datetime, handled by Rsc with DateTime
Root namespace for the PLCnext API
Contains information to marshall an array
Definition: RscType.hpp:130
size_t Size
Count of array elements
Definition: RscType.hpp:142
size_t FieldCount
Count of Fields of struct element type
Definition: RscType.hpp:157
size_t Dimensions
Array Dimensions
Definition: RscType.hpp:147
RscType ElementType
Array element type
Definition: RscType.hpp:152