Apollo  6.0
Open source self driving car software
simulation_world_service.h
Go to the documentation of this file.
1 /******************************************************************************
2  * Copyright 2017 The Apollo Authors. All Rights Reserved.
3  *
4  * Licensed under the Apache License, Version 2.0 (the "License");
5  * you may not use this file except in compliance with the License.
6  * You may obtain a copy of the License at
7  *
8  * http://www.apache.org/licenses/LICENSE-2.0
9  *
10  * Unless required by applicable law or agreed to in writing, software
11  * distributed under the License is distributed on an "AS IS" BASIS,
12  * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13  * See the License for the specific language governing permissions and
14  * limitations under the License.
15  *****************************************************************************/
16 
21 #pragma once
22 
23 #include <algorithm>
24 #include <list>
25 #include <memory>
26 #include <string>
27 #include <unordered_map>
28 #include <utility>
29 #include <vector>
30 
31 #include <boost/thread/locks.hpp>
32 #include <boost/thread/shared_mutex.hpp>
33 
34 #include "gtest/gtest_prod.h"
35 
36 #include "nlohmann/json.hpp"
37 
38 #include "modules/audio/proto/audio.pb.h"
39 #include "modules/audio/proto/audio_event.pb.h"
40 #include "modules/common/proto/drive_event.pb.h"
41 #include "modules/common/proto/pnc_point.pb.h"
42 #include "modules/control/proto/control_cmd.pb.h"
43 #include "modules/dreamview/proto/simulation_world.pb.h"
44 #include "modules/localization/proto/gps.pb.h"
45 #include "modules/localization/proto/localization.pb.h"
46 #include "modules/perception/proto/traffic_light_detection.pb.h"
47 #include "modules/planning/proto/planning.pb.h"
48 #include "modules/planning/proto/planning_internal.pb.h"
49 #include "modules/prediction/proto/prediction_obstacle.pb.h"
50 #include "modules/storytelling/proto/story.pb.h"
51 #include "modules/task_manager/proto/task_manager.pb.h"
52 
53 #include "cyber/common/log.h"
56 
61 namespace apollo {
62 namespace dreamview {
63 
73  public:
74  // The maximum number of monitor message items to be kept in
75  // SimulationWorld.
76  static constexpr int kMaxMonitorItems = 30;
77 
83  SimulationWorldService(const MapService *map_service,
84  bool routing_from_file = false);
85 
90  inline const SimulationWorld &world() const { return world_; }
91 
98  nlohmann::json GetUpdateAsJson(double radius) const;
99 
107  void GetWireFormatString(double radius, std::string *sim_world,
108  std::string *sim_world_with_planning_data);
109 
116  nlohmann::json GetMapElements(double radius) const;
117 
123  void Update();
124 
128  void SetToClear() { to_clear_ = true; }
129 
135  bool ReadyToPush() const { return ready_to_push_.load(); }
136 
144  apollo::common::monitor::MonitorMessageItem::LogLevel log_level,
145  const std::string &msg);
146 
148  const std::shared_ptr<apollo::relative_map::NavigationInfo> &);
150  const std::shared_ptr<apollo::routing::RoutingRequest> &);
151 
152  void PublishTask(const std::shared_ptr<apollo::task_manager::Task> &);
153 
154  void GetMapElementIds(double radius, MapElementIds *ids) const;
155 
156  const apollo::hdmap::Map &GetRelativeMap() const;
157 
158  nlohmann::json GetRoutePathAsJson() const;
159 
160  void DumpMessages();
161 
162  private:
163  void InitReaders();
164  void InitWriters();
165 
170  template <typename DataType>
171  void UpdateSimulationWorld(const DataType &data);
172 
173  void UpdateMonitorMessages();
174 
175  Object &CreateWorldObjectIfAbsent(
176  const apollo::perception::PerceptionObstacle &obstacle);
177  void CreateWorldObjectFromSensorMeasurement(
178  const apollo::perception::SensorMeasurement &sensor,
179  Object *world_object);
180  void SetObstacleInfo(const apollo::perception::PerceptionObstacle &obstacle,
181  Object *world_object);
182  void SetObstaclePolygon(
183  const apollo::perception::PerceptionObstacle &obstacle,
184  Object *world_object);
185  void SetObstacleSensorMeasurements(
186  const apollo::perception::PerceptionObstacle &obstacle,
187  Object *world_object);
188  void SetObstacleSource(const apollo::perception::PerceptionObstacle &obstacle,
189  Object *world_object);
190  void UpdatePlanningTrajectory(
191  const apollo::planning::ADCTrajectory &trajectory);
192  void UpdateRSSInfo(const apollo::planning::ADCTrajectory &trajectory);
193  bool LocateMarker(const apollo::planning::ObjectDecisionType &decision,
194  Decision *world_decision);
195  void FindNudgeRegion(const apollo::planning::ObjectDecisionType &decision,
196  const Object &world_obj, Decision *world_decision);
197  void UpdateDecision(const apollo::planning::DecisionResult &decision_res,
198  double header_time);
199  void UpdateMainStopDecision(
200  const apollo::planning::MainDecision &main_decision,
201  double update_timestamp_sec, Object *world_main_stop);
202 
203  template <typename MainDecision>
204  void UpdateMainChangeLaneDecision(const MainDecision &decision,
205  Object *world_main_decision) {
206  if (decision.has_change_lane_type() &&
207  (decision.change_lane_type() == apollo::routing::ChangeLaneType::LEFT ||
208  decision.change_lane_type() ==
209  apollo::routing::ChangeLaneType::RIGHT)) {
210  auto *change_lane_decision = world_main_decision->add_decision();
211  change_lane_decision->set_change_lane_type(decision.change_lane_type());
212 
213  const auto &adc = world_.auto_driving_car();
214  change_lane_decision->set_position_x(adc.position_x());
215  change_lane_decision->set_position_y(adc.position_y());
216  change_lane_decision->set_heading(adc.heading());
217  }
218  }
219 
220  void CreatePredictionTrajectory(
221  const apollo::prediction::PredictionObstacle &obstacle,
222  Object *world_object);
223 
224  void DownsamplePath(const apollo::common::Path &paths,
225  apollo::common::Path *downsampled_path);
226 
227  void UpdatePlanningData(const apollo::planning_internal::PlanningData &data);
228 
229  void PopulateMapInfo(double radius);
230 
235  template <typename MessageT>
236  void UpdateWithLatestObserved(cyber::Reader<MessageT> *reader,
237  bool logging = true) {
238  if (reader->Empty()) {
239  if (logging) {
240  AINFO_EVERY(100) << "Has not received any data from "
241  << reader->GetChannelName();
242  }
243  return;
244  }
245 
246  const std::shared_ptr<MessageT> msg = reader->GetLatestObserved();
247  UpdateSimulationWorld(*msg);
248  }
249 
254  template <typename MessageT>
255  void DumpMessageFromReader(cyber::Reader<MessageT> *reader) {
256  if (reader->Empty()) {
257  AWARN << "Has not received any data from " << reader->GetChannelName()
258  << ". Cannot dump message!";
259  return;
260  }
261 
263  }
264 
265  void ReadRoutingFromFile(const std::string &routing_response_file);
266 
267  template <typename MessageT>
268  void UpdateLatency(const std::string &module_name,
269  cyber::Reader<MessageT> *reader) {
270  if (reader->Empty()) {
271  return;
272  }
273 
274  const auto header = reader->GetLatestObserved()->header();
275  const double publish_time_sec = header.timestamp_sec();
276  const double sensor_time_sec =
278  std::max({header.lidar_timestamp(), header.camera_timestamp(),
279  header.radar_timestamp()}))
280  .ToSecond();
281 
282  Latency latency;
283  latency.set_timestamp_sec(publish_time_sec);
284  latency.set_total_time_ms((publish_time_sec - sensor_time_sec) * 1.0e3);
285  (*world_.mutable_latency())[module_name] = latency;
286  }
287 
295  void UpdateDelays();
296 
302  void UpdateLatencies();
303 
304  template <typename Points>
305  void DownsampleSpeedPointsByInterval(const Points &points,
306  size_t downsampleInterval,
307  Points *downsampled_points) {
308  if (points.empty()) {
309  return;
310  }
311 
312  for (int i = 0; i + 1 < points.size(); i += downsampleInterval) {
313  *downsampled_points->Add() = points[i];
314  }
315 
316  // add the last point
317  *downsampled_points->Add() = *points.rbegin();
318  }
319 
320  std::unique_ptr<cyber::Node> node_;
321 
322  // The underlying SimulationWorld object, owned by the
323  // SimulationWorldService instance.
324  SimulationWorld world_;
325 
326  // Downsampled route paths to be rendered in frontend.
327  mutable boost::shared_mutex route_paths_mutex_;
328  std::vector<RoutePath> route_paths_;
329 
330  // The handle of MapService, not owned by SimulationWorldService.
331  const MapService *map_service_;
332 
333  // The map holding obstacle string id to the actual object
334  std::unordered_map<std::string, Object> obj_map_;
335 
336  // A temporary cache for all the monitor messages coming in.
337  std::mutex monitor_msgs_mutex_;
338  std::list<std::shared_ptr<common::monitor::MonitorMessage>> monitor_msgs_;
339 
340  // The SIMULATOR monitor for publishing messages.
341  apollo::common::monitor::MonitorLogBuffer monitor_logger_buffer_;
342 
343  // Whether to clear the SimulationWorld in the next timer cycle, set by
344  // frontend request.
345  bool to_clear_ = false;
346 
347  // Relative map used/retrieved in navigation mode
348  apollo::hdmap::Map relative_map_;
349 
350  // Whether the sim_world is ready to push to frontend
351  std::atomic<bool> ready_to_push_;
352 
353  // Latest rss info
354  double current_real_dist_ = 0.0;
355  double current_rss_safe_dist_ = 0.0;
356 
357  // Gear Location
358  apollo::canbus::Chassis_GearPosition gear_location_;
359 
360  // Readers.
361  std::shared_ptr<cyber::Reader<apollo::canbus::Chassis>> chassis_reader_;
362  std::shared_ptr<cyber::Reader<apollo::localization::Gps>> gps_reader_;
363  std::shared_ptr<cyber::Reader<apollo::localization::LocalizationEstimate>>
364  localization_reader_;
365  std::shared_ptr<cyber::Reader<apollo::perception::PerceptionObstacles>>
366  perception_obstacle_reader_;
367  std::shared_ptr<cyber::Reader<apollo::perception::TrafficLightDetection>>
368  perception_traffic_light_reader_;
369  std::shared_ptr<cyber::Reader<apollo::prediction::PredictionObstacles>>
370  prediction_obstacle_reader_;
371  std::shared_ptr<cyber::Reader<apollo::planning::ADCTrajectory>>
372  planning_reader_;
373  std::shared_ptr<cyber::Reader<apollo::control::ControlCommand>>
374  control_command_reader_;
375  std::shared_ptr<cyber::Reader<apollo::relative_map::NavigationInfo>>
376  navigation_reader_;
377  std::shared_ptr<cyber::Reader<apollo::relative_map::MapMsg>>
378  relative_map_reader_;
379  std::shared_ptr<cyber::Reader<apollo::audio::AudioEvent>> audio_event_reader_;
380  std::shared_ptr<cyber::Reader<apollo::common::DriveEvent>>
381  drive_event_reader_;
382  std::shared_ptr<cyber::Reader<apollo::common::monitor::MonitorMessage>>
383  monitor_reader_;
384  std::shared_ptr<cyber::Reader<apollo::routing::RoutingRequest>>
385  routing_request_reader_;
386  std::shared_ptr<cyber::Reader<apollo::routing::RoutingResponse>>
387  routing_response_reader_;
388  std::shared_ptr<cyber::Reader<apollo::storytelling::Stories>>
389  storytelling_reader_;
390  std::shared_ptr<cyber::Reader<apollo::audio::AudioDetection>>
391  audio_detection_reader_;
392  std::shared_ptr<cyber::Reader<apollo::task_manager::Task>> task_reader_;
393 
394  // Writers.
395  std::shared_ptr<cyber::Writer<apollo::relative_map::NavigationInfo>>
396  navigation_writer_;
397  std::shared_ptr<cyber::Writer<apollo::routing::RoutingRequest>>
398  routing_request_writer_;
399  std::shared_ptr<cyber::Writer<apollo::routing::RoutingResponse>>
400  routing_response_writer_;
401  std::shared_ptr<cyber::Writer<apollo::task_manager::Task>> task_writer_;
402 
403  FRIEND_TEST(SimulationWorldServiceTest, UpdateMonitorSuccess);
404  FRIEND_TEST(SimulationWorldServiceTest, UpdateMonitorRemove);
405  FRIEND_TEST(SimulationWorldServiceTest, UpdateMonitorTruncate);
406  FRIEND_TEST(SimulationWorldServiceTest, UpdateChassisInfo);
407  FRIEND_TEST(SimulationWorldServiceTest, UpdateLatency);
408  FRIEND_TEST(SimulationWorldServiceTest, UpdateLocalization);
409  FRIEND_TEST(SimulationWorldServiceTest, UpdatePerceptionObstacles);
410  FRIEND_TEST(SimulationWorldServiceTest, UpdatePlanningTrajectory);
411  FRIEND_TEST(SimulationWorldServiceTest, UpdateDecision);
412  FRIEND_TEST(SimulationWorldServiceTest, UpdatePrediction);
413  FRIEND_TEST(SimulationWorldServiceTest, UpdateRouting);
414  FRIEND_TEST(SimulationWorldServiceTest, UpdateGps);
415  FRIEND_TEST(SimulationWorldServiceTest, UpdateControlCommandWithSimpleLonLat);
416  FRIEND_TEST(SimulationWorldServiceTest, UpdateControlCommandWithSimpleMpc);
417  FRIEND_TEST(SimulationWorldServiceTest, DownsampleSpeedPointsByInterval);
418 };
419 
420 } // namespace dreamview
421 } // namespace apollo
void PublishNavigationInfo(const std::shared_ptr< apollo::relative_map::NavigationInfo > &)
::apollo::cyber::Time Time
Definition: racobit_radar_message_manager.h:41
void PublishRoutingRequest(const std::shared_ptr< apollo::routing::RoutingRequest > &)
bool ReadyToPush() const
Check whether the SimulationWorld object has enough information. The backend won&#39;t push the Simulatio...
Definition: simulation_world_service.h:135
static constexpr int kMaxMonitorItems
Definition: simulation_world_service.h:76
nlohmann::json GetMapElements(double radius) const
Returns the json representation of the map element Ids and hash within the given radius from the car...
const SimulationWorld & world() const
Get a read-only view of the SimulationWorld.
Definition: simulation_world_service.h:90
PlanningContext is the runtime context in planning. It is persistent across multiple frames...
Definition: atomic_hash_map.h:25
void GetMapElementIds(double radius, MapElementIds *ids) const
nlohmann::json GetUpdateAsJson(double radius) const
Returns the json representation of the SimulationWorld object. This is a public API used by offline d...
nlohmann::json GetRoutePathAsJson() const
Reader subscribes a channel, it has two main functions:
Definition: reader.h:68
Definition: map_service.h:40
This is a major component of the Simulation backend, which maintains a SimulationWorld object and kee...
Definition: simulation_world_service.h:72
const apollo::hdmap::Map & GetRelativeMap() const
bool DumpMessage(const std::shared_ptr< T > &msg, const std::string &dump_dir="/tmp")
Definition: message_util.h:57
void PublishMonitorMessage(apollo::common::monitor::MonitorMessageItem::LogLevel log_level, const std::string &msg)
Publish message to the monitor.
const std::string & GetChannelName() const
Get Reader&#39;s Channel name.
Definition: reader_base.h:125
void Update()
The function Update() is periodically called to check for updates from the external messages...
bool Empty() const override
Query whether the Reader has data to be handled.
Definition: reader.h:355
void SetToClear()
Sets the flag to clear the owned simulation world object.
Definition: simulation_world_service.h:128
virtual std::shared_ptr< MessageT > GetLatestObserved() const
Get the latest message we Observe
Definition: reader.h:377
void PublishTask(const std::shared_ptr< apollo::task_manager::Task > &)
SimulationWorldService(const MapService *map_service, bool routing_from_file=false)
Constructor of SimulationWorldService.
The class of MonitorLogBuffer.
double ToSecond() const
convert time to second.
#define AWARN
Definition: log.h:43
void GetWireFormatString(double radius, std::string *sim_world, std::string *sim_world_with_planning_data)
Returns the binary representation of the SimulationWorld object.
#define AINFO_EVERY(freq)
Definition: log.h:82
This class help collect MonitorMessage pb to monitor topic. The messages can be published automatical...
Definition: monitor_log_buffer.h:60