1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
#![allow(non_camel_case_types)]
#![allow(non_snake_case)]
#![allow(non_upper_case_globals)]
mod bindings;
pub use bindings::*;
#[cfg(feature = "osqp_dlong")]
pub type osqp_int = ::std::os::raw::c_longlong;
#[cfg(not(feature = "osqp_dlong"))]
pub type osqp_int = ::std::os::raw::c_int;
pub type osqp_float = f64;
type c_int = osqp_int;
type c_float = osqp_float;
pub enum OSQPTimer {}
#[cfg(test)]
mod tests {
use std::mem;
use super::*;
extern "C" {
fn free(ptr: *mut u8);
fn csc_matrix(
m: c_int,
n: c_int,
nzmax: c_int,
x: *mut c_float,
i: *mut c_int,
p: *mut c_int,
) -> *mut csc;
}
#[test]
fn osqp_demo_rust() {
unsafe {
osqp_demo_rust_unsafe();
}
}
unsafe fn osqp_demo_rust_unsafe() {
let mut P_x: [c_float; 4] = [4.0, 1.0, 1.0, 2.0];
let P_nnz: c_int = 4;
let mut P_i: [c_int; 4] = [0, 1, 0, 1];
let mut P_p: [c_int; 3] = [0, 2, 4];
let mut q: [c_float; 2] = [1.0, 1.0];
let mut A_x: [c_float; 4] = [1.0, 1.0, 1.0, 1.0];
let A_nnz: c_int = 4;
let mut A_i: [c_int; 4] = [0, 1, 0, 2];
let mut A_p: [c_int; 3] = [0, 2, 4];
let mut l: [c_float; 3] = [1.0, 0.0, 0.0];
let mut u: [c_float; 3] = [1.0, 0.7, 0.7];
let n: c_int = 2;
let m: c_int = 3;
let P = csc_matrix(
n,
n,
P_nnz,
P_x.as_mut_ptr(),
P_i.as_mut_ptr(),
P_p.as_mut_ptr(),
);
let A = csc_matrix(
m,
n,
A_nnz,
A_x.as_mut_ptr(),
A_i.as_mut_ptr(),
A_p.as_mut_ptr(),
);
let mut data: OSQPData = mem::zeroed();
data.n = n;
data.m = m;
data.P = P;
data.q = q.as_mut_ptr();
data.A = A;
data.l = l.as_mut_ptr();
data.u = u.as_mut_ptr();
let data = &data as *const OSQPData;
let mut settings: OSQPSettings = mem::zeroed();
osqp_set_default_settings(&mut settings);
settings.alpha = 1.0;
settings.adaptive_rho = 0;
let settings = &mut settings as *mut OSQPSettings;
let work: *mut OSQPWorkspace = osqp_setup(data, settings);
*(data as *mut OSQPData) = mem::zeroed();
*settings = mem::zeroed();
*P = mem::zeroed();
*A = mem::zeroed();
osqp_solve(work);
let eps = 1e-9;
let x = (*(*work).solution).x;
let x0 = *x;
let x1 = *(x.offset(1));
println!("[{}, {}]", x0, x1);
assert!((0.2987710845986426 - x0).abs() < eps);
assert!((0.701227995544065 - x1).abs() < eps);
osqp_cleanup(work);
free(A as *mut u8);
free(P as *mut u8);
}
}