#include "Rover.h"
static const uint16_t CRASH_CHECK_TRIGGER_SEC = 2;
static const float CRASH_CHECK_THROTTLE_MIN = 5.0f;
static const float CRASH_CHECK_VEL_MIN = 0.08f;
void Rover::crash_check()
{
static uint16_t crash_counter;
bool crashed = false;
if (!arming.is_armed() || g.fs_crash_check == FS_CRASH_DISABLE || ((!control_mode->is_autopilot_mode()) && (!is_balancebot()))) {
crash_counter = 0;
return;
}
if ((g2.crash_angle != 0) && ((fabsf(ahrs.get_pitch_rad()) > radians(g2.crash_angle)) || (fabsf(ahrs.get_roll_rad()) > radians(g2.crash_angle)))) {
crashed = true;
}
if (!is_balancebot()) {
if (!crashed && ((ahrs.groundspeed() >= CRASH_CHECK_VEL_MIN) ||
(fabsf(ahrs.get_gyro().z) >= CRASH_CHECK_VEL_MIN) ||
(fabsf(g2.motors.get_throttle()) < CRASH_CHECK_THROTTLE_MIN))) {
crash_counter = 0;
return;
}
crash_counter++;
if (crash_counter >= (CRASH_CHECK_TRIGGER_SEC * 10)) {
crashed = true;
}
}
if (crashed) {
LOGGER_WRITE_ERROR(LogErrorSubsystem::CRASH_CHECK,
LogErrorCode::CRASH_CHECK_CRASH);
if (is_balancebot()) {
GCS_SEND_TEXT(MAV_SEVERITY_EMERGENCY, "Crash: Disarming");
arming.disarm(AP_Arming::Method::CRASH);
} else {
GCS_SEND_TEXT(MAV_SEVERITY_EMERGENCY, "Crash: Going to HOLD");
set_mode(mode_hold, ModeReason::CRASH_FAILSAFE);
if (g.fs_crash_check == FS_CRASH_HOLD_AND_DISARM) {
arming.disarm(AP_Arming::Method::CRASH);
}
}
}
}