opcua_protocol_addon.cpp
Go to the documentation of this file.
1 
11 
12 #include "opcua_protocol.h"
13 
14 #include "opc_tcp_processor.h"
15 #include "endpoints_parameters.h"
16 #include "tcp_server.h"
17 
18 #include <opc/common/logger.h>
19 #include <opc/common/uri_facade.h>
23 #include <opc/ua/protocol/utils.h>
27 
28 #include <stdexcept>
29 
30 
31 namespace
32 {
33 
34 using namespace OpcUa;
35 using namespace OpcUa::Binary;
36 using namespace OpcUa::Server;
37 
39 {
40 public:
41  OpcTcp(OpcUa::Services::SharedPtr services, const Common::Logger::SharedPtr & logger)
42  : Server(services)
43  , Logger(logger)
44  {
45  }
46 
47  virtual void Process(OpcUa::IOChannel::SharedPtr clientChannel)
48  {
49  if (!clientChannel)
50  {
51  LOG_WARN(Logger, "opc_tcp_processor| empty channel passed to endpoints opc binary protocol processor");
52 
53  return;
54  }
55 
56  LOG_DEBUG(Logger, "opc_tcp_processor| Hello client!");
57 
58  std::shared_ptr<OpcTcpMessages> messageProcessor = std::make_shared<OpcTcpMessages>(Server, clientChannel, Logger);
59 
60  for (;;)
61  {
62  ProcessData(*clientChannel, *messageProcessor);
63  }
64  }
65 
66  virtual void StopProcessing(OpcUa::IOChannel::SharedPtr clientChannel)
67  {
68  }
69 
70 private:
71  void ProcessData(OpcUa::IOChannel & clientChannel, OpcUa::Server::OpcTcpMessages & messageProcessor)
72  {
73  using namespace OpcUa::Binary;
74 
75  IStreamBinary iStream(clientChannel);
76  ProcessChunk(iStream, messageProcessor);
77  }
78 
79  // TODO implement collecting full message from chunks before processing.
80  void ProcessChunk(IStreamBinary & iStream, OpcTcpMessages & messageProcessor)
81  {
82  LOG_DEBUG(Logger, "opc_tcp_processor| processing new chunk");
83 
84  Header hdr;
85  // Receive message header.
86  iStream >> hdr;
87 
88  // Receive full message.
89  std::vector<char> buffer(hdr.MessageSize());
90  OpcUa::Binary::RawBuffer buf(&buffer[0], buffer.size());
91  iStream >> buf;
92 
93  LOG_DEBUG(Logger, "opc_tcp_processor| received message:\n{}", ToHexDump(buffer));
94 
95  // restrict server size code only with current message.
96  OpcUa::InputFromBuffer messageChannel(&buffer[0], buffer.size());
97  IStreamBinary messageStream(messageChannel);
98  messageProcessor.ProcessMessage(hdr.Type, messageStream);
99 
100  if (messageChannel.GetRemainSize())
101  {
102  LOG_ERROR(Logger, "opc_tcp_processor| message has not been processed completely");
103  }
104  }
105 
106 private:
107  OpcUa::Services::SharedPtr Server;
108  Common::Logger::SharedPtr Logger;
109 };
110 
112 {
113 public:
115 
116 public:
117  OpcUaProtocol(OpcUa::Server::TcpServer & tcpServer, const Common::Logger::SharedPtr & logger)
118  : TcpAddon(tcpServer)
119  , Logger(logger)
120  {
121  }
122 
123  virtual void StartEndpoints(const std::vector<EndpointDescription> & endpoints, OpcUa::Services::SharedPtr server) override
124  {
125  for (const EndpointDescription endpoint : endpoints)
126  {
127  const Common::Uri uri(endpoint.EndpointUrl);
128 
129  if (uri.Scheme() == "opc.tcp")
130  {
131  std::shared_ptr<IncomingConnectionProcessor> processor(new OpcTcp(server, Logger));
132  TcpParameters tcpParams;
133  tcpParams.Port = uri.Port();
134 
135  LOG_INFO(Logger, "opc_tcp_processor| start to listen on port {}", tcpParams.Port);
136 
137  TcpAddon.Listen(tcpParams, processor);
138  Ports.push_back(tcpParams);
139  }
140  }
141  }
142 
143  virtual void StopEndpoints() override
144  {
145  for (const TcpParameters & params : Ports)
146  {
147  TcpAddon.StopListen(params);
148  }
149  }
150 
151 private:
152  OpcUa::Server::TcpServer & TcpAddon;
153  std::vector<TcpParameters> Ports;
154  Common::Logger::SharedPtr Logger;
155 };
156 
157 
158 class OpcUaProtocolAddon : public Common::Addon
159 {
160 public:
161  OpcUaProtocolAddon()
162  {
163  }
164 
165 public: // Common::Addon
166  virtual void Initialize(Common::AddonsManager & addons, const Common::AddonParameters & params) override;
167  virtual void Stop() override;
168 
169 private:
170  void ApplyAddonParameters(const Common::AddonParameters & params);
171  // not used
172  // void PublishApplicationsInformation(std::vector<OpcUa::ApplicationDescription> applications, std::vector<OpcUa::EndpointDescription> endpoints, const Common::AddonsManager& addons) const;
173 
174 private:
175  OpcUa::Server::ServicesRegistry::SharedPtr InternalServer;
176  OpcUa::Server::TcpServer::SharedPtr TcpServer;
177  OpcUa::Server::OpcUaProtocol::SharedPtr Protocol;
178  Common::Logger::SharedPtr Logger;
179 };
180 
181 void OpcUaProtocolAddon::Initialize(Common::AddonsManager & addons, const Common::AddonParameters & params)
182 {
183  Logger = addons.GetLogger();
184  ApplyAddonParameters(params);
185  const std::vector<OpcUa::Server::ApplicationData> applications = OpcUa::ParseEndpointsParameters(params.Groups, Logger);
186 
187  for (OpcUa::Server::ApplicationData d : applications)
188  {
189  LOG_INFO(Logger, "endpoint is: {}", d.Endpoints.front().EndpointUrl);
190  }
191 
192  std::vector<OpcUa::ApplicationDescription> applicationDescriptions;
193  std::vector<OpcUa::EndpointDescription> endpointDescriptions;
194 
195  for (const OpcUa::Server::ApplicationData application : applications)
196  {
197  applicationDescriptions.push_back(application.Application);
198  endpointDescriptions.insert(endpointDescriptions.end(), application.Endpoints.begin(), application.Endpoints.end());
199  }
200 
201  OpcUa::Server::EndpointsRegistry::SharedPtr endpointsAddon = addons.GetAddon<OpcUa::Server::EndpointsRegistry>(OpcUa::Server::EndpointsRegistryAddonId);
202 
203  if (!endpointsAddon)
204  {
205  LOG_ERROR(Logger, "cannot store endpoints information, endpoints service addon has not been registered");
206  return;
207  }
208 
209  endpointsAddon->AddEndpoints(endpointDescriptions);
210  endpointsAddon->AddApplications(applicationDescriptions);
211 
213 
215  Protocol.reset(new OpcUaProtocol(*TcpServer, Logger));
216  Protocol->StartEndpoints(endpointDescriptions, InternalServer->GetServer());
217 }
218 
219 void OpcUaProtocolAddon::Stop()
220 {
221  Protocol.reset();
222  TcpServer.reset();
223  InternalServer.reset();
224 }
225 
226 void OpcUaProtocolAddon::ApplyAddonParameters(const Common::AddonParameters & params)
227 {
228  /*
229  for (const Common::Parameter parameter : params.Parameters)
230  {
231  if (parameter.Name == "debug" && !parameter.Value.empty() && parameter.Value != "0")
232  {
233  Debug = true;
234  std::cout << "Enabled debug mode in the binary protocol addon." << std::endl;
235  }
236  }
237  */
238 }
239 
240 // not used
241 //void OpcUaProtocolAddon::PublishApplicationsInformation(std::vector<OpcUa::ApplicationDescription> applications, std::vector<OpcUa::EndpointDescription> endpoints, const Common::AddonsManager& addons) const
242 //{
243 // OpcUa::Server::EndpointsRegistry::SharedPtr endpointsAddon = addons.GetAddon<OpcUa::Server::EndpointsRegistry>(OpcUa::Server::EndpointsRegistryAddonId);
244 // if (!endpointsAddon)
245 // {
246 // std::cerr << "Cannot save information about endpoints. Endpoints services addon didn't' registered." << std::endl;
247 // return;
248 // }
249 // endpointsAddon->AddEndpoints(endpoints);
250 // endpointsAddon->AddApplications(applications);
251 //}
252 
253 } // namespace
254 
255 
256 namespace OpcUa
257 {
258 namespace Server
259 {
260 Common::Addon::UniquePtr OpcUaProtocolAddonFactory::CreateAddon()
261 {
262  return Common::Addon::UniquePtr(new ::OpcUaProtocolAddon());
263 }
264 
265 
266 OpcUaProtocol::UniquePtr CreateOpcUaProtocol(TcpServer & tcpServer, const Common::Logger::SharedPtr & logger)
267 {
268  return OpcUaProtocol::UniquePtr(new ::OpcUaProtocol(tcpServer, logger));
269 }
270 
271 }
272 }
d
Common::Addon * CreateAddon()
Addon interface definition GNU LGPL.
virtual const Logger::SharedPtr & GetLogger() const
Definition: addon_manager.h:90
const char EndpointsRegistryAddonId[]
#define LOG_WARN(__logger__,...)
Definition: common/logger.h:26
Addon interface definition GNU LGPL.
virtual std::shared_ptr< Addon > GetAddon(const AddonId &id) const =0
getting addon by id
#define LOG_ERROR(__logger__,...)
Definition: common/logger.h:27
#define LOG_DEBUG(__logger__,...)
Definition: common/logger.h:24
const char ServicesRegistryAddonId[]
bool ProcessMessage(Binary::MessageType msgType, Binary::IStreamBinary &iStream)
#define LOG_INFO(__logger__,...)
Definition: common/logger.h:25
OPC UA Address space part. GNU LGPL.
string uri
Definition: client.py:31
std::string ToHexDump(const char *buf, std::size_t size)
Definition: utils.h:29
std::vector< Server::ApplicationData > ParseEndpointsParameters(const std::vector< Common::ParametersGroup > &rootGroup, const Common::Logger::SharedPtr &logger)
#define DEFINE_CLASS_POINTERS(ClassName)
Exception declarations GNU LGPL.
std::vector< ParametersGroup > Groups
TcpServer::UniquePtr CreateTcpServer(const Common::Logger::SharedPtr &logger)
Definition: tcp_server.cpp:338
OpcUaProtocol::UniquePtr CreateOpcUaProtocol(TcpServer &tcpServer, const Common::Logger::SharedPtr &logger)
const char Server[]
Definition: strings.h:121
Definition: server.py:1


ros_opcua_impl_freeopcua
Author(s): Denis Štogl
autogenerated on Tue Jan 19 2021 03:12:07