32 #include "generated/modules.h"
35 #ifndef SITL // no chibios threads in sim
37 #error Only Chibios is supported
47 #define WE_UKF_KI 0.f // >= 0 to ensure that covariance is positive semi-definite
50 #define WE_UKF_ALPHA 0.5f // sigma point dispersion
53 #define WE_UKF_BETA 2.f // 2 is the best choice when distribution is gaussian
56 #define WE_UKF_P0 0.2f // initial covariance diagonal element
59 #define WE_UKF_R_GS 0.5f // ground speed measurement confidence
62 #define WE_UKF_R_VA 0.5f // airspeed measurement confidence
65 #define WE_UKF_R_AOA 0.002f // angle of attack measurement confidence
68 #define WE_UKF_R_SSA 0.002f // sideslip angle measurement confidence
71 #define WE_UKF_Q_VA 0.1f // airspeed model confidence
73 #ifndef WE_UKF_Q_VA_SCALE
74 #define WE_UKF_Q_VA_SCALE 0.0001f // airspeed scale factor model confidence
77 #define WE_UKF_Q_WIND 0.001f // wind model confidence
80 #ifndef SEND_WIND_ESTIMATOR
81 #define SEND_WIND_ESTIMATOR TRUE
91 pprz_msg_send_WIND_INFO_RET(trans, dev, AC_ID,
99 #if PERIODIC_TELEMETRY
103 #ifndef LOG_WIND_ESTIMATOR
104 #define LOG_WIND_ESTIMATOR FALSE
107 #if LOG_WIND_ESTIMATOR
110 #define PrintLog sdLogWriteLog
111 #define LogFileIsOpen() (pprzLogFile != -1)
112 #else // SITL: print in a file
114 #define PrintLog fprintf
115 #define LogFileIsOpen() (pprzLogFile != NULL)
118 static bool log_we_started;
122 #define MAT_EL(_m, _l, _c, _n) _m[_l + _c * _n]
208 #if LOG_WIND_ESTIMATOR
209 if (LogFileIsOpen()) {
210 if (!log_we_started) {
215 for (i = 0; i < 7; i++)
219 for (i = 0; i < 5; i++)
226 PrintLog(
pprzLogFile,
"p q r ax ay az q1 q2 q3 q4 vkx vky vkz va aoa ssa u v w wx wy wz vas t\n");
227 log_we_started =
true;
229 PrintLog(
pprzLogFile,
"%.5f %.5f %.5f %.3f %.3f %.3f %.4f %.4f %.4f %.4f %.5f %.5f %.5f %.5f %.5f %.5f ",
272 #if LOG_WIND_ESTIMATOR
273 if (log_we_started) {
274 PrintLog(
pprzLogFile,
"%.3f %.3f %.3f %.3f %.3f %.3f %.3f %d\n",
297 if (chMtxTryLock(&we_ukf_mtx)) {
326 struct FloatVect3 gravity_ned = { 0.f, 0.f, 9.81f };
327 struct FloatVect3 gravity_body = { 0.f, 0.f, 0.f };
334 accel_body.
x += -9.81*sinf(b2i_e->
theta);
335 accel_body.
y += 9.81*cosf(b2i_e->
theta)*sinf(b2i_e->
phi);
336 accel_body.
z += 9.81*cosf(b2i_e->
theta)*cosf(b2i_e->
phi);
400 chMtxUnlock(&we_ukf_mtx);
402 chSemSignal(&we_ukf_sem);
416 if (chMtxTryLock(&we_ukf_mtx)) {
427 #if SEND_WIND_ESTIMATOR
434 chMtxUnlock(&we_ukf_mtx);
447 chRegSetThreadName(
"wind estimation");
451 chSemWait(&we_ukf_sem);
453 chMtxLock(&we_ukf_mtx);
457 chMtxUnlock(&we_ukf_mtx);
469 #if LOG_WIND_ESTIMATOR
470 log_we_started =
false;
476 snprintf(filename, 512,
"%s/we_ukf_%05d.csv", STRINGIFY(WE_LOG_PATH), counter);
480 snprintf(filename, 512,
"%s/we_ukf_%05d.csv", STRINGIFY(WE_LOG_PATH), ++counter);
484 printf(
"Failed to open WE log file '%s'\n",filename);
486 printf(
"Opening WE log file '%s'\n",filename);
493 chThdCreateStatic(wa_thd_windestimation,
sizeof(wa_thd_windestimation),
497 #if PERIODIC_TELEMETRY
void wind_estimator_Set_R_AOA(float _v)
#define VECT3_ADD(_a, _b)
float q_va
noise associated to airspeed vector model
void init_calculator(void)
bool data_available
new data available
void wind_estimator_Set_Q_VA_SCALE(float _v)
static struct FloatEulers * stateGetNedToBodyEulers_f(void)
Get vehicle body attitude euler angles (float).
static MUTEX_DECL(we_ukf_mtx)
Periodic telemetry system header (includes downlink utility and generated code).
float r_aoa
noise associated to angle of attack measurement
uint32_t get_sys_time_msec(void)
Get the time in milliseconds since startup.
static void wind_estimator_step(void)
void UKF_Wind_Estimator_step(void)
static float stateGetAirspeed_f(void)
Get airspeed (float).
float q_va_scale
noise associated to airspeed scale factor model
struct WindEstimator wind_estimator
void wind_estimator_init(void)
float r_ssa
noise associated to sideslip angle measurement
float q_wind
noise associated to wind vector model
struct Imu imu
global IMU state
void wind_estimator_Set_R_VA(float _v)
void wind_estimator_Set_Q_WIND(float _v)
static struct FloatQuat * stateGetNedToBodyQuat_f(void)
Get vehicle body attitude quaternion (float).
static struct FloatRMat * stateGetNedToBodyRMat_f(void)
Get vehicle body attitude rotation matrix (float).
static float float_vect3_norm(struct FloatVect3 *v)
Paparazzi floating point math for geodetic calculations.
static void send_wind_estimator(struct transport_tx *trans, struct link_device *dev)
void wind_estimator_Set_Q_VA(float _v)
void float_rmat_vmult(struct FloatVect3 *vb, struct FloatRMat *m_a2b, struct FloatVect3 *va)
rotate 3D vector by rotation matrix.
struct Int32Vect3 accel
accelerometer measurements in m/s^2 in BFP with INT32_ACCEL_FRAC
Paparazzi floating point algebra.
static struct NedCoor_f * stateGetSpeedNed_f(void)
Get ground speed in local NED coordinates (float).
Architecture independent timing functions.
static struct NedCoor_f * stateGetAccelNed_f(void)
Get acceleration in NED coordinates (float).
#define ACCEL_FLOAT_OF_BFP(_ai)
Wind Estimator based on generated library from Matlab.
static uint32_t time_step_before
#define DefaultPeriodic
Set default periodic telemetry.
static SEMAPHORE_DECL(we_ukf_sem, 0)
#define WE_UKF_KI
Default parameters.
#define WE_UKF_Q_VA_SCALE
Inertial Measurement Unit interface.
static float stateGetAngleOfAttack_f(void)
Get angle of attack (float).
static struct FloatRates * stateGetBodyRates_f(void)
Get vehicle body angular rate (float).
void wind_estimator_Set_R_SSA(float _v)
bool reset
reset filter flag
static const struct usb_device_descriptor dev
void UKF_Wind_Estimator_initialize(void)
static void stateSetVerticalWindspeed_f(float v_windspeed)
Set vertical windspeed (float).
API to get/set the generic vehicle states.
void wind_estimator_periodic(void)
float r_gs
noise associated to ground speed measurement
static float stateGetSideslip_f(void)
Get sideslip (float).
struct FloatVect3 airspeed
airspeed vector in body frame
static void thd_windestimate(void *arg)
static THD_WORKING_AREA(wa_thd_windestimation, 8 *1024)
Common code for AP and FBW telemetry.
#define MAT_EL(_m, _l, _c, _n)
ukf_params_type ukf_params
void wind_estimator_event(void)
uint8_t msg[10]
Buffer used for general comunication over SPI (out buffer)
struct FloatVect3 wind
wind vector in NED frame
int8_t register_periodic_telemetry(struct periodic_telemetry *_pt, uint8_t _id, telemetry_cb _cb)
Register a telemetry callback function.
float r_va
noise associated to airspeed norm measurement
void wind_estimator_Set_R_GS(float _v)
static void stateSetHorizontalWindspeed_f(struct FloatVect2 *h_windspeed)
Set horizontal windspeed (float).