source: finroc_plugins_data_ports/optimized/tSingleThreadedCheapCopyPortGeneric.cpp @ 114:8b171b809697

17.03
Last change on this file since 114:8b171b809697 was 114:8b171b809697, checked in by Max Reichardt <mreichardt@…>, 2 years ago

Removes obsolete reverse pushing mechanism (as this is an unused feature in C++ that comes with a performance penalty, makes the implementation more complex, and does not properly work with the new type conversion feature).

File size: 7.7 KB
Line 
1//
2// You received this file as part of Finroc
3// A framework for intelligent robot control
4//
5// Copyright (C) Finroc GbR (finroc.org)
6//
7// This program is free software; you can redistribute it and/or modify
8// it under the terms of the GNU General Public License as published by
9// the Free Software Foundation; either version 2 of the License, or
10// (at your option) any later version.
11//
12// This program is distributed in the hope that it will be useful,
13// but WITHOUT ANY WARRANTY; without even the implied warranty of
14// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
15// GNU General Public License for more details.
16//
17// You should have received a copy of the GNU General Public License along
18// with this program; if not, write to the Free Software Foundation, Inc.,
19// 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA.
20//
21//----------------------------------------------------------------------
22/*!\file    plugins/data_ports/optimized/tSingleThreadedCheapCopyPortGeneric.cpp
23 *
24 * \author  Max Reichardt
25 *
26 * \date    2014-06-22
27 *
28 */
29//----------------------------------------------------------------------
30#include "plugins/data_ports/optimized/tSingleThreadedCheapCopyPortGeneric.h"
31
32//----------------------------------------------------------------------
33// External includes (system with <>, local with "")
34//----------------------------------------------------------------------
35
36//----------------------------------------------------------------------
37// Internal includes with ""
38//----------------------------------------------------------------------
39#include "plugins/data_ports/optimized/cheaply_copied_types.h"
40
41//----------------------------------------------------------------------
42// Debugging
43//----------------------------------------------------------------------
44#include <cassert>
45
46//----------------------------------------------------------------------
47// Namespace usage
48//----------------------------------------------------------------------
49
50//----------------------------------------------------------------------
51// Namespace declaration
52//----------------------------------------------------------------------
53namespace finroc
54{
55namespace data_ports
56{
57namespace optimized
58{
59
60//----------------------------------------------------------------------
61// Forward declarations / typedefs / enums
62//----------------------------------------------------------------------
63
64//----------------------------------------------------------------------
65// Const values
66//----------------------------------------------------------------------
67
68//----------------------------------------------------------------------
69// Implementation
70//----------------------------------------------------------------------
71
72tSingleThreadedCheapCopyPortGeneric::tSingleThreadedCheapCopyPortGeneric(common::tAbstractDataPortCreationInfo creation_info) :
73  common::tAbstractDataPort(creation_info),
74  current_value(),
75  default_value(),
76  max_queue_length(-1),
77  standard_assign(!GetFlag(tFlag::NON_STANDARD_ASSIGN) && (!GetFlag(tFlag::HAS_QUEUE)))
78{
79  current_value.data.reset(creation_info.data_type.CreateGenericObject());
80  current_value.data_pointer = current_value.data->GetRawDataPointer();
81  current_value.cheaply_copyable_type_index = RegisterPort(creation_info.data_type);
82  current_value.timestamp = rrlib::time::cNO_TIME;
83
84  if ((!IsDataFlowType(GetDataType())) || (!IsCheaplyCopiedType(GetDataType())))
85  {
86    FINROC_LOG_PRINT(ERROR, "Data type ", GetDataType().GetName(), " is not suitable for cheap copy port implementation.");
87    abort();
88  }
89
90  // set initial value to default?
91  if (creation_info.DefaultValueSet() || creation_info.flags.Get(core::tFrameworkElement::tFlag::DEFAULT_ON_DISCONNECT))
92  {
93    default_value.reset(creation_info.data_type.CreateGenericObject());
94    if (creation_info.DefaultValueSet())
95    {
96      rrlib::serialization::tInputStream stream(creation_info.GetDefaultGeneric());
97      default_value->Deserialize(stream);
98    }
99    current_value.data->DeepCopyFrom(*default_value);
100  }
101
102  // Queues are only supported in subclass
103}
104
105tSingleThreadedCheapCopyPortGeneric::~tSingleThreadedCheapCopyPortGeneric()
106{}
107
108void tSingleThreadedCheapCopyPortGeneric::ApplyDefaultValue()
109{
110  if (!default_value)
111  {
112    FINROC_LOG_PRINT(ERROR, "No default value has been set. Doing nothing.");
113    return;
114  }
115  BrowserPublishRaw(*default_value, rrlib::time::cNO_TIME, true);
116}
117
118std::string tSingleThreadedCheapCopyPortGeneric::BrowserPublishRaw(const rrlib::rtti::tGenericObject& buffer, rrlib::time::tTimestamp timestamp,
119    bool notify_listener_on_this_port, tChangeStatus change_constant)
120{
121  current_value.data->DeepCopyFrom(buffer);
122  current_value.timestamp = timestamp;
123  common::tPublishOperation<tSingleThreadedCheapCopyPortGeneric, tPublishingData> publish_operation(current_value);
124  if (notify_listener_on_this_port)
125  {
126    if (change_constant == tChangeStatus::CHANGED_INITIAL)
127    {
128      publish_operation.Execute<tChangeStatus::CHANGED_INITIAL, true, true>(*this);
129    }
130    else
131    {
132      publish_operation.Execute<tChangeStatus::CHANGED, true, true>(*this);
133    }
134  }
135  else
136  {
137    if (change_constant == tChangeStatus::CHANGED_INITIAL)
138    {
139      publish_operation.Execute<tChangeStatus::CHANGED_INITIAL, true, false>(*this);
140    }
141    else
142    {
143      publish_operation.Execute<tChangeStatus::CHANGED, true, false>(*this);
144    }
145  }
146  return "";
147}
148
149void tSingleThreadedCheapCopyPortGeneric::ForwardData(tAbstractDataPort& other)
150{
151  assert(IsDataFlowType(other.GetDataType()) && (IsCheaplyCopiedType(other.GetDataType())));
152
153  common::tPublishOperation<tSingleThreadedCheapCopyPortGeneric, tPublishingData> publish_operation(current_value);
154  publish_operation.Execute<tChangeStatus::CHANGED, false, false>(static_cast<tSingleThreadedCheapCopyPortGeneric&>(other));
155}
156
157int tSingleThreadedCheapCopyPortGeneric::GetMaxQueueLengthImplementation() const
158{
159  return max_queue_length;
160}
161
162void tSingleThreadedCheapCopyPortGeneric::InitialPushTo(core::tConnector& connector)
163{
164  common::tPublishOperation<tSingleThreadedCheapCopyPortGeneric, tPublishingData> data(current_value);
165  tSingleThreadedCheapCopyPortGeneric& target_port = static_cast<tSingleThreadedCheapCopyPortGeneric&>(connector.Destination());
166  common::tPublishOperation<tSingleThreadedCheapCopyPortGeneric, tPublishingData>::Receive<tChangeStatus::CHANGED_INITIAL>(data, target_port, *this);
167}
168
169bool tSingleThreadedCheapCopyPortGeneric::NonStandardAssign(tPublishingData& publishing_data, tChangeStatus change_constant)
170{
171  throw std::logic_error("Only implemented for/in subclasses");
172}
173
174void tSingleThreadedCheapCopyPortGeneric::Publish(const rrlib::rtti::tGenericObject& data, rrlib::time::tTimestamp timestamp)
175{
176  if (!GetFlag(tFlag::HIJACKED_PORT))
177  {
178    current_value.data->DeepCopyFrom(data);
179    current_value.timestamp = timestamp;
180    common::tPublishOperation<tSingleThreadedCheapCopyPortGeneric, tPublishingData> publish_operation(current_value);
181    publish_operation.Execute<tChangeStatus::CHANGED, false, false>(*this);
182  }
183}
184
185void tSingleThreadedCheapCopyPortGeneric::SetCurrentValueBuffer(void* address)
186{
187  std::unique_ptr<rrlib::rtti::tGenericObject> new_buffer(GetDataType().CreateGenericObject(address));
188  new_buffer->DeepCopyFrom(*current_value.data);
189  std::swap(new_buffer, current_value.data);
190  current_value.data_pointer = current_value.data->GetRawDataPointer();
191}
192
193void tSingleThreadedCheapCopyPortGeneric::SetDefault(rrlib::rtti::tGenericObject& new_default)
194{
195  default_value.reset(new_default.GetType().CreateGenericObject());
196  default_value->DeepCopyFrom(new_default);
197  current_value.data->DeepCopyFrom(new_default);
198}
199
200
201//----------------------------------------------------------------------
202// End of namespace declaration
203//----------------------------------------------------------------------
204}
205}
206}
Note: See TracBrowser for help on using the repository browser.