129 {
130
131
132
133 bool succ = true;
134
135 std::vector<c_float> P_data;
136 std::vector<c_int> P_indices;
137 std::vector<c_int> P_indptr;
138 assembleP(&P_data, &P_indices, &P_indptr);
139 if (check_mode_) {
140 AINFO <<
"print P_data in whole: ";
141 printMatrix(num_of_variables_, num_of_variables_, P_data, P_indices,
142 P_indptr);
143 }
144
145 c_float q[num_of_variables_];
146 for (int i = 0; i < num_of_variables_; ++i) {
147 q[i] = 0.0;
148 if (i >= s_start_index_) {
149 q[i] = beta_;
150 }
151 }
152
153
154 std::vector<c_float> A_data;
155 std::vector<c_int> A_indices;
156 std::vector<c_int> A_indptr;
158 if (check_mode_) {
159 AINFO <<
"print A_data in whole: ";
160 printMatrix(num_of_constraints_, num_of_variables_, A_data, A_indices,
161 A_indptr);
162 assembleA(num_of_constraints_, num_of_variables_, A_data, A_indices,
163 A_indptr);
164 }
165
166
167 c_float lb[num_of_constraints_];
168 c_float ub[num_of_constraints_];
169 int slack_indx = num_of_constraints_ - slack_horizon_;
170 for (int i = 0; i < num_of_constraints_; ++i) {
171 lb[i] = 0.0;
172 if (i >= slack_indx) {
173 lb[i] = -2e19;
174 }
175
176 if (i < 2 * obstacles_num_ * (horizon_ + 1)) {
177 ub[i] = 0.0;
178 } else if (i < slack_indx) {
179 ub[i] = 2e19;
180 } else {
181 ub[i] = 0.0;
182 }
183 }
184
185
186 OSQPSettings* settings =
187 reinterpret_cast<OSQPSettings*>(c_malloc(sizeof(OSQPSettings)));
188
189
190 osqp_set_default_settings(settings);
191 settings->alpha = osqp_config_.
alpha();
192 settings->eps_abs = osqp_config_.
eps_abs();
193 settings->eps_rel = osqp_config_.
eps_rel();
194 settings->max_iter = osqp_config_.
max_iter();
195 settings->polish = osqp_config_.
polish();
197
198
199 OSQPData* data = reinterpret_cast<OSQPData*>(c_malloc(sizeof(OSQPData)));
200 data->n = num_of_variables_;
201 data->m = num_of_constraints_;
202 data->P = csc_matrix(data->n, data->n, P_data.size(), P_data.data(),
203 P_indices.data(), P_indptr.data());
204 data->q = q;
205 data->A = csc_matrix(data->m, data->n, A_data.size(), A_data.data(),
206 A_indices.data(), A_indptr.data());
207 data->l = lb;
208 data->u = ub;
209
210
211 OSQPWorkspace* work = nullptr;
212
213 work = osqp_setup(data, settings);
214
215
216 osqp_solve(work);
217
218
219 if (work->info->status_val != 1 && work->info->status_val != 2) {
220 AWARN <<
"OSQP dual warm up unsuccess, "
221 << "return status: " << work->info->status;
222 succ = false;
223 }
224
225
226 std::vector<double> lambda_norm;
227 int l_index = l_start_index_;
228 for (int i = 0; i < horizon_ + 1; ++i) {
229 int edges_counter = 0;
230 for (int j = 0; j < obstacles_num_; ++j) {
231 int current_edges_num = obstacles_edges_num_(j, 0);
232 Eigen::MatrixXd Aj =
233 obstacles_A_.block(edges_counter, 0, current_edges_num, 2);
234
235 double tmp1 = 0;
236 double tmp2 = 0;
237 for (int k = 0; k < current_edges_num; ++k) {
238 tmp1 += Aj(k, 0) * work->solution->x[l_index + k];
239 tmp2 += Aj(k, 1) * work->solution->x[l_index + k];
240 }
241
242
243 double tmp_norm = tmp1 * tmp1 + tmp2 * tmp2;
244 if (tmp_norm >= 1e-5) {
245 lambda_norm.push_back(0.75 / std::sqrt(tmp_norm));
246 } else {
247 lambda_norm.push_back(0.0);
248 }
249
250 edges_counter += current_edges_num;
251 l_index += current_edges_num;
252 }
253 }
254
255
256 int variable_index = 0;
257
258
259 for (int i = 0; i < horizon_ + 1; ++i) {
260 int r_index = 0;
261 for (int j = 0; j < obstacles_num_; ++j) {
262 for (int k = 0; k < obstacles_edges_num_(j, 0); ++k) {
263 l_warm_up_(r_index, i) = lambda_norm[i * obstacles_num_ + j] *
264 work->solution->x[variable_index];
265 ++variable_index;
266 ++r_index;
267 }
268 }
269 }
270
271
272 for (int i = 0; i < horizon_ + 1; ++i) {
273 int r_index = 0;
274 for (int j = 0; j < obstacles_num_; ++j) {
275 for (int k = 0; k < 4; ++k) {
276 n_warm_up_(r_index, i) = lambda_norm[i * obstacles_num_ + j] *
277 work->solution->x[variable_index];
278 ++r_index;
279 ++variable_index;
280 }
281 }
282 }
283
284
285 for (int i = 0; i < horizon_ + 1; ++i) {
286 for (int j = 0; j < obstacles_num_; ++j) {
287 slacks_(j, i) = lambda_norm[i * obstacles_num_ + j] *
288 work->solution->x[variable_index];
289 ++variable_index;
290 }
291 }
292
293 succ = succ & (work->info->obj_val <= 1.0);
294
295
296 osqp_cleanup(work);
297 c_free(data->A);
298 c_free(data->P);
299 c_free(data);
300 c_free(settings);
301
302 return succ;
303}
void assembleP(std::vector< c_float > *P_data, std::vector< c_int > *P_indices, std::vector< c_int > *P_indptr)
void assembleA(const int r, const int c, const std::vector< c_float > &P_data, const std::vector< c_int > &P_indices, const std::vector< c_int > &P_indptr)
void printMatrix(const int r, const int c, const std::vector< c_float > &P_data, const std::vector< c_int > &P_indices, const std::vector< c_int > &P_indptr)
void assembleConstraint(std::vector< c_float > *A_data, std::vector< c_int > *A_indices, std::vector< c_int > *A_indptr)
optional bool osqp_debug_log