Apollo 10.0
自动驾驶开放平台
v2x_proxy.cc
浏览该文件的文档.
1/******************************************************************************
2 * Copyright 2018 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 *****************************************************************************/
21
22#include <cmath>
23#include <cstdio>
24#include <ostream>
25#include <vector>
26
28
29namespace apollo {
30namespace v2x {
31using ::apollo::canbus::ChassisDetail;
32using ::apollo::v2x::CarStatus;
33using ::apollo::v2x::StatusResponse;
34using ::apollo::v2x::obu::ObuRsi;
35using ::apollo::v2x::obu::ObuTrafficLight;
36
38 if (recv_thread_ != nullptr && recv_thread_->joinable()) {
39 recv_thread_->join();
40 }
41 if (planning_thread_ != nullptr && planning_thread_->joinable()) {
42 planning_thread_->join();
43 }
44 if (obs_thread_ != nullptr && obs_thread_->joinable()) {
45 obs_thread_->join();
46 }
47}
48
49V2xProxy::V2xProxy(std::shared_ptr<::apollo::hdmap::HDMap> hdmap)
50 : node_(::apollo::cyber::CreateNode("v2x_proxy")), exit_(false) {
51 if (node_ == nullptr) {
52 AFATAL << "Create v2x proxy node failed.";
53 exit(1);
54 }
55 internal_ = std::make_shared<InternalData>();
56 hdmap_ = std::make_shared<::apollo::hdmap::HDMap>();
57 const auto hdmap_file = apollo::hdmap::BaseMapFile();
58 if (0 != hdmap_->LoadMapFromFile(hdmap_file)) {
59 AERROR << "Failed to load hadmap file: " << hdmap_file;
60 return;
61 }
62 ::apollo::cyber::TimerOption v2x_car_status_timer_option;
63 v2x_car_status_timer_option.period =
64 static_cast<uint32_t>((1000 + FLAGS_v2x_car_status_timer_frequency - 1) /
65 FLAGS_v2x_car_status_timer_frequency);
66 v2x_car_status_timer_option.callback = [this]() {
67 this->OnV2xCarStatusTimer();
68 };
69 v2x_car_status_timer_option.oneshot = false;
70 v2x_car_status_timer_.reset(
71 new ::apollo::cyber::Timer(v2x_car_status_timer_option));
72 os_interface_.reset(new OsInterFace());
73 obu_interface_.reset(new ObuInterFaceGrpcImpl());
74 recv_thread_.reset(new std::thread([this]() {
75 while (!exit_.load()) {
76 this->RecvTrafficlight();
77 }
78 }));
79 CHECK(!!hdmap_ && !!v2x_car_status_timer_);
80 CHECK(!!os_interface_ && !!obu_interface_);
81 CHECK(os_interface_->InitFlag() && obu_interface_->InitFlag());
82 planning_thread_.reset(new std::thread([this]() {
83 while (!exit_.load()) {
84 this->RecvOsPlanning();
85 }
86 }));
87 obs_thread_.reset(new std::thread([this]() {
88 while (!exit_.load()) {
89 std::shared_ptr<::apollo::v2x::V2XObstacles> obs = nullptr;
90 this->obu_interface_->GetV2xObstaclesFromObu(&obs); // Blocked
91 this->os_interface_->SendV2xObstacles2Sys(obs);
92 }
93 }));
94 v2x_car_status_timer_->Start();
95 GetRsuListFromFile(FLAGS_rsu_whitelist_name, &rsu_list_);
96 init_flag_ = true;
97}
98
99bool V2xProxy::GetRsuListFromFile(const std::string &filename,
100 std::set<std::string> *whitelist) {
101 if (nullptr == whitelist) {
102 return false;
103 }
104 std::ifstream input_file(filename);
105 if (!input_file) {
106 return false;
107 }
108 std::string line;
109 while (getline(input_file, line)) {
110 whitelist->insert(line);
111 }
112 return !whitelist->empty();
113}
114
115bool V2xProxy::InitFlag() { return init_flag_; }
116
117void V2xProxy::RecvOsPlanning() {
118 auto adc_trajectory = std::make_shared<::apollo::planning::ADCTrajectory>();
119 auto res_light =
120 std::make_shared<::apollo::perception::TrafficLightDetection>();
121 os_interface_->GetPlanningAdcFromOs(adc_trajectory);
122 // OK get planning message
123 std::shared_ptr<OSLight> last_os_light = nullptr;
124 {
125 std::lock_guard<std::mutex> lock(lock_last_os_light_);
126
128 if (last_os_light_ == nullptr ||
129 2000LL * 1000 * 1000 < now_us - ts_last_os_light_) {
130 AWARN << "V2X Traffic Light is too old!";
131 last_os_light_ = nullptr;
132 } else {
133 ADEBUG << "V2X Traffic Light is on time.";
134 last_os_light = std::make_shared<OSLight>();
135 last_os_light->CopyFrom(*last_os_light_);
136 }
137 }
138 // proc planning message
139 bool res_proc_planning_msg = internal_->ProcPlanningMessage(
140 adc_trajectory.get(), last_os_light.get(), &res_light);
141 if (!res_proc_planning_msg) {
142 return;
143 }
144 os_interface_->SendV2xTrafficLight4Hmi2Sys(res_light);
145}
146
147void V2xProxy::RecvTrafficlight() {
148 // get traffic light from obu
149 std::shared_ptr<ObuLight> x2v_traffic_light = nullptr;
150 obu_interface_->GetV2xTrafficLightFromObu(&x2v_traffic_light);
151 os_interface_->SendV2xObuTrafficLightToOs(x2v_traffic_light);
152 auto os_light = std::make_shared<OSLight>();
153 std::string junction_id = "";
154 {
155 std::lock_guard<std::mutex> lg(lock_hdmap_junction_id_);
156 junction_id = hdmap_junction_id_;
157 }
158 bool res_success_ProcTrafficlight = internal_->ProcTrafficlight(
159 hdmap_, x2v_traffic_light.get(), junction_id, u_turn_,
160 FLAGS_traffic_light_distance, FLAGS_check_time, &os_light);
161 if (!res_success_ProcTrafficlight) {
162 return;
163 }
164 utils::UniqueOslight(os_light.get());
165 os_interface_->SendV2xTrafficLightToOs(os_light);
166 // save for hmi
167 std::lock_guard<std::mutex> lock(lock_last_os_light_);
168 ts_last_os_light_ = ::apollo::cyber::Time::MonoTime().ToMicrosecond();
169 last_os_light_ = os_light;
170}
171
172double cal_distance(const ::apollo::common::PointENU &p1,
173 const ::apollo::common::PointENU &p2) {
174 double x = p1.x() - p2.x();
175 double y = p1.y() - p2.y();
176 return std::sqrt(x * x + y * y);
177}
178
179void V2xProxy::OnV2xCarStatusTimer() {
180 // get loc
181 auto localization =
182 std::make_shared<::apollo::localization::LocalizationEstimate>();
183 os_interface_->GetLocalizationFromOs(localization);
184 if (nullptr == localization) {
185 return;
186 }
187 std::set<std::string> rsu_whitelist;
188 {
189 std::lock_guard<std::mutex> lg(rsu_list_mutex_);
190 rsu_whitelist.insert(rsu_list_.cbegin(), rsu_list_.cend());
191 }
192 ::apollo::common::PointENU car_position;
193 car_position.set_x(localization->pose().position().x());
194 car_position.set_y(localization->pose().position().y());
195 std::shared_ptr<::apollo::v2x::CarStatus> v2x_car_status = nullptr;
196 double heading = 0.0;
197 std::string res_junction_id = "";
198 bool ret_get_rsu_info = utils::GetRsuInfo(
199 hdmap_, *localization, rsu_whitelist, FLAGS_traffic_light_distance,
200 FLAGS_heading_difference, &v2x_car_status, &res_junction_id, &heading);
201 {
202 std::lock_guard<std::mutex> lg(lock_hdmap_junction_id_);
203 hdmap_junction_id_ = res_junction_id;
204 }
205 if (!ret_get_rsu_info) {
206 return;
207 }
208 // calc heading
209 if (!init_heading_) {
210 heading_ = heading;
211 init_heading_ = true;
212 }
213 if (std::fabs(heading_ - heading) > 1.0) {
214 u_turn_ = true;
215 }
216 obu_interface_->SendCarStatusToObu(v2x_car_status);
217}
218
219} // namespace v2x
220} // namespace apollo
uint64_t ToMicrosecond() const
convert time to microsecond (us).
Definition time.cc:85
static Time MonoTime()
Definition time.cc:67
V2xProxy(std::shared_ptr<::apollo::hdmap::HDMap > hdmap=nullptr)
Definition v2x_proxy.cc:49
bool GetRsuListFromFile(const std::string &filename, std::set< std::string > *whitelist)
Definition v2x_proxy.cc:99
#define ADEBUG
Definition log.h:41
#define AERROR
Definition log.h:44
#define AFATAL
Definition log.h:45
#define AWARN
Definition log.h:43
std::string BaseMapFile()
get base map file path from flags.
Definition hdmap_util.cc:47
bool GetRsuInfo(const std::shared_ptr<::apollo::hdmap::HDMap > &hdmap, const OSLocation &os_location, const std::set< std::string > &rsu_whitelist, double distance, double max_heading_difference, std::shared_ptr<::apollo::v2x::CarStatus > *v2x_car_status, std::string *out_junction_id, double *out_heading)
Definition utils.cc:417
void UniqueOslight(OSLight *os_light)
Definition utils.cc:495
double cal_distance(const ::apollo::common::PointENU &p1, const ::apollo::common::PointENU &p2)
Definition v2x_proxy.cc:172
class register implement
Definition arena_queue.h:37
The options of timer
Definition timer.h:32
uint32_t period
The period of the timer, unit is ms max: 512 * 64 min: 1
Definition timer.h:54
bool oneshot
True: perform the callback only after the first timing cycle False: perform the callback every timed ...
Definition timer.h:63
std::function< void()> callback
The task that the timer needs to perform
Definition timer.h:57
define v2x proxy class
The gflags used by v2x proxy module