mirror of
https://github.com/dragonpilot/dragonpilot.git
synced 2026-06-27 00:42:05 +08:00
Squashed 'panda/' changes from 293fa33..9ee6285
9ee6285 optimize board build for size to avoid going over the limit. (#150) 20e8fa9 Start introducing Bounties a2046e9 make it smaller 1dfcf2b update panda price 37ee289 chrysler safety: fixed comments c2dfbad tesla safety: return -1 to block forward (#149) 74c0c1b update README be0061d Chrysler: safety now based on motor torque 039d183 Chrysler: fixed regression test 9193eeb Chrysler: safety limits updated 04f1d44 Chrysler safety: 3 sa max rate down for now cf3ecd6 Chrysler safety: re-using hyundai framework 49ed9bc Update CLICKS for longer bootup time of EONS and avoid unwanted fast charge mode git-subtree-dir: panda git-subtree-split: 9ee628557f3f33759c62b567964b918a597d3387
This commit is contained in:
@@ -3,7 +3,7 @@ Welcome to panda
|
||||
|
||||
[panda](http://github.com/commaai/panda) is the nicest universal car interface ever.
|
||||
|
||||
<a href="https://www.amazon.com/chffr-panda-OBD-II-Interface/dp/B07D6Y3GN2/"><img src="https://github.com/commaai/panda/blob/master/panda.png">
|
||||
<a href="https://comma.ai/shop/products/panda-obd-ii-dongle"><img src="https://github.com/commaai/panda/blob/master/panda.png">
|
||||
|
||||
<img src="https://github.com/commaai/panda/blob/master/buy.png"></a>
|
||||
|
||||
|
||||
@@ -51,6 +51,9 @@ void fail() {
|
||||
// know where to sig check
|
||||
extern void *_app_start[];
|
||||
|
||||
// FIXME: sometimes your panda will fail flashing and will quickly blink a single Green LED
|
||||
// BOUNTY: $200 coupon on shop.comma.ai or $100 check.
|
||||
|
||||
int main() {
|
||||
__disable_irq();
|
||||
clock_init();
|
||||
|
||||
+3
-1
@@ -1,4 +1,4 @@
|
||||
CFLAGS += -I inc -I ../ -nostdlib -fno-builtin -std=gnu11 -O2
|
||||
CFLAGS += -I inc -I ../ -nostdlib -fno-builtin -std=gnu11 -Os
|
||||
|
||||
CFLAGS += -Tstm32_flash.ld
|
||||
|
||||
@@ -51,6 +51,8 @@ obj/$(PROJ_NAME).bin: obj/$(STARTUP_FILE).o obj/main.$(PROJ_NAME).o
|
||||
$(CC) -Wl,--section-start,.isr_vector=0x8004000 $(CFLAGS) -o obj/$(PROJ_NAME).elf $^
|
||||
$(OBJCOPY) -v -O binary obj/$(PROJ_NAME).elf obj/code.bin
|
||||
SETLEN=1 ../crypto/sign.py obj/code.bin $@ $(CERT)
|
||||
@BINSIZE=$$(du -b "obj/$(PROJ_NAME).bin" | cut -f 1) ; if [ $$BINSIZE -ge 32768 ]; then echo "ERROR obj/$(PROJ_NAME).bin is too big!"; exit 1; fi;
|
||||
|
||||
|
||||
obj/bootstub.$(PROJ_NAME).bin: obj/$(STARTUP_FILE).o obj/bootstub.$(PROJ_NAME).o obj/sha.$(PROJ_NAME).o obj/rsa.$(PROJ_NAME).o
|
||||
$(CC) $(CFLAGS) -o obj/bootstub.$(PROJ_NAME).elf $^
|
||||
|
||||
+4
-2
@@ -589,6 +589,8 @@ int main() {
|
||||
uint64_t marker = 0;
|
||||
#define CURRENT_THRESHOLD 0xF00
|
||||
#define CLICKS 8
|
||||
// Enough clicks to ensure that enumeration happened. Should be longer than bootup time of the device connected to EON
|
||||
#define CLICKS_BOOTUP 30
|
||||
#endif
|
||||
|
||||
for (cnt=0;;cnt++) {
|
||||
@@ -615,8 +617,8 @@ int main() {
|
||||
}
|
||||
break;
|
||||
case USB_POWER_CDP:
|
||||
// been CLICKS clicks since we switched to CDP
|
||||
if ((cnt-marker) >= CLICKS) {
|
||||
// been CLICKS_BOOTUP clicks since we switched to CDP
|
||||
if ((cnt-marker) >= CLICKS_BOOTUP ) {
|
||||
// measure current draw, if positive and no enumeration, switch to DCP
|
||||
if (!is_enumerated && current < CURRENT_THRESHOLD) {
|
||||
puts("USBP: no enumeration with current draw, switching to DCP mode\n");
|
||||
|
||||
@@ -1,20 +1,19 @@
|
||||
// board enforces
|
||||
// in-state
|
||||
// ACC is active (green)
|
||||
// out-state
|
||||
// brake pressed
|
||||
// stock LKAS ECU is online
|
||||
// ACC is not active (white or disabled)
|
||||
const int CHRYSLER_MAX_STEER = 261;
|
||||
const int CHRYSLER_MAX_RT_DELTA = 112; // max delta torque allowed for real time checks
|
||||
const int32_t CHRYSLER_RT_INTERVAL = 250000; // 250ms between real time checks
|
||||
const int CHRYSLER_MAX_RATE_UP = 3;
|
||||
const int CHRYSLER_MAX_RATE_DOWN = 3;
|
||||
const int CHRYSLER_MAX_TORQUE_ERROR = 80; // max torque cmd in excess of torque motor
|
||||
|
||||
// chrysler_: namespacing
|
||||
int chrysler_speed = 0;
|
||||
|
||||
// silence everything if stock ECUs are still online
|
||||
int chrysler_lkas_detected = 0;
|
||||
int chrysler_camera_detected = 0;
|
||||
int chrysler_rt_torque_last = 0;
|
||||
int chrysler_desired_torque_last = 0;
|
||||
int chrysler_cruise_engaged_last = 0;
|
||||
uint32_t chrysler_ts_last = 0;
|
||||
struct sample_t chrysler_torque_meas; // last few torques measured
|
||||
|
||||
static void chrysler_rx_hook(CAN_FIFOMailBox_TypeDef *to_push) {
|
||||
int bus_number = (to_push->RDTR >> 4) & 0xFF;
|
||||
int bus = (to_push->RDTR >> 4) & 0xFF;
|
||||
uint32_t addr;
|
||||
if (to_push->RIR & 4) {
|
||||
// Extended
|
||||
@@ -26,40 +25,37 @@ static void chrysler_rx_hook(CAN_FIFOMailBox_TypeDef *to_push) {
|
||||
addr = to_push->RIR >> 21;
|
||||
}
|
||||
|
||||
if (addr == 0x144 && bus_number == 0) {
|
||||
chrysler_speed = ((to_push->RDLR & 0xFF000000) >> 16) | (to_push->RDHR & 0xFF);
|
||||
// Measured eps torque
|
||||
if (addr == 544) {
|
||||
int rdhr = to_push->RDHR;
|
||||
int torque_meas_new = ((rdhr & 0x7) << 8) + ((rdhr & 0xFF00) >> 8) - 1024;
|
||||
|
||||
// update array of samples
|
||||
update_sample(&chrysler_torque_meas, torque_meas_new);
|
||||
}
|
||||
|
||||
// check if stock LKAS ECU is still online
|
||||
if (addr == 0x292 && bus_number == 0) {
|
||||
chrysler_lkas_detected = 1;
|
||||
controls_allowed = 0;
|
||||
}
|
||||
|
||||
// ["ACC_2"]['ACC_STATUS_2'] == 7 for active (green) Adaptive Cruise Control
|
||||
if (addr == 0x1f4 && bus_number == 0) {
|
||||
if (((to_push->RDLR & 0x380000) >> 19) == 7) {
|
||||
// enter controls on rising edge of ACC, exit controls on ACC off
|
||||
if (addr == 0x1f4) {
|
||||
int cruise_engaged = ((to_push->RDLR & 0x380000) >> 19) == 7;
|
||||
if (cruise_engaged && !chrysler_cruise_engaged_last) {
|
||||
controls_allowed = 1;
|
||||
} else {
|
||||
} else if (!cruise_engaged) {
|
||||
controls_allowed = 0;
|
||||
}
|
||||
chrysler_cruise_engaged_last = cruise_engaged;
|
||||
}
|
||||
|
||||
// exit controls on brake press by human
|
||||
if (addr == 0x140) {
|
||||
if (to_push->RDLR & 0x4) {
|
||||
controls_allowed = 0;
|
||||
}
|
||||
// check if stock camera ECU is still online
|
||||
if (bus == 0 && addr == 0x292) {
|
||||
chrysler_camera_detected = 1;
|
||||
controls_allowed = 0;
|
||||
}
|
||||
}
|
||||
|
||||
// if controls_allowed
|
||||
// allow steering up to limit
|
||||
// else
|
||||
// block all commands that produce actuation
|
||||
static int chrysler_tx_hook(CAN_FIFOMailBox_TypeDef *to_send) {
|
||||
// There can be only one! (LKAS)
|
||||
if (chrysler_lkas_detected) {
|
||||
|
||||
// There can be only one! (camera)
|
||||
if (chrysler_camera_detected) {
|
||||
return 0;
|
||||
}
|
||||
|
||||
@@ -72,65 +68,69 @@ static int chrysler_tx_hook(CAN_FIFOMailBox_TypeDef *to_send) {
|
||||
addr = to_send->RIR >> 21;
|
||||
}
|
||||
|
||||
// LKA STEER: Too large of values cause the steering actuator ECU to silently
|
||||
// fault and no longer actuate the wheel until the car is rebooted.
|
||||
|
||||
// LKA STEER
|
||||
if (addr == 0x292) {
|
||||
int rdlr = to_send->RDLR;
|
||||
int straight = 1024;
|
||||
int steer = ((rdlr & 0x7) << 8) + ((rdlr & 0xFF00) >> 8) - straight;
|
||||
int max_steer = 230;
|
||||
int max_rate = 50; // ECU is fine with 100, but 3 is typical.
|
||||
if (steer > max_steer) {
|
||||
return false;
|
||||
}
|
||||
if (steer < -max_steer) {
|
||||
return false;
|
||||
}
|
||||
if (!controls_allowed && steer != 0) {
|
||||
// If controls not allowed, only allow steering to move closer to 0.
|
||||
if (chrysler_desired_torque_last == 0) {
|
||||
return false;
|
||||
}
|
||||
if ((chrysler_desired_torque_last > 0) && (steer >= chrysler_desired_torque_last)) {
|
||||
return false;
|
||||
}
|
||||
if ((chrysler_desired_torque_last < 0) && (steer <= chrysler_desired_torque_last)) {
|
||||
return false;
|
||||
int desired_torque = ((rdlr & 0x7) << 8) + ((rdlr & 0xFF00) >> 8) - 1024;
|
||||
uint32_t ts = TIM2->CNT;
|
||||
int violation = 0;
|
||||
|
||||
if (controls_allowed) {
|
||||
|
||||
// *** global torque limit check ***
|
||||
violation |= max_limit_check(desired_torque, CHRYSLER_MAX_STEER, -CHRYSLER_MAX_STEER);
|
||||
|
||||
// *** torque rate limit check ***
|
||||
violation |= dist_to_meas_check(desired_torque, chrysler_desired_torque_last,
|
||||
&chrysler_torque_meas, CHRYSLER_MAX_RATE_UP, CHRYSLER_MAX_RATE_DOWN, CHRYSLER_MAX_TORQUE_ERROR);
|
||||
|
||||
// used next time
|
||||
chrysler_desired_torque_last = desired_torque;
|
||||
|
||||
// *** torque real time rate limit check ***
|
||||
violation |= rt_rate_limit_check(desired_torque, chrysler_rt_torque_last, CHRYSLER_MAX_RT_DELTA);
|
||||
|
||||
// every RT_INTERVAL set the new limits
|
||||
uint32_t ts_elapsed = get_ts_elapsed(ts, chrysler_ts_last);
|
||||
if (ts_elapsed > CHRYSLER_RT_INTERVAL) {
|
||||
chrysler_rt_torque_last = desired_torque;
|
||||
chrysler_ts_last = ts;
|
||||
}
|
||||
}
|
||||
if (steer < (chrysler_desired_torque_last - max_rate)) {
|
||||
|
||||
// no torque if controls is not allowed
|
||||
if (!controls_allowed && (desired_torque != 0)) {
|
||||
violation = 1;
|
||||
}
|
||||
|
||||
// reset to 0 if either controls is not allowed or there's a violation
|
||||
if (violation || !controls_allowed) {
|
||||
chrysler_desired_torque_last = 0;
|
||||
chrysler_rt_torque_last = 0;
|
||||
chrysler_ts_last = ts;
|
||||
}
|
||||
|
||||
if (violation) {
|
||||
return false;
|
||||
}
|
||||
if (steer > (chrysler_desired_torque_last + max_rate)) {
|
||||
return false;
|
||||
}
|
||||
|
||||
chrysler_desired_torque_last = steer;
|
||||
}
|
||||
|
||||
// FORCE CANCEL: safety check only relevant when spamming the cancel button.
|
||||
// ensuring that only the cancel button press is sent when controls are off.
|
||||
// This avoids unintended engagements while still allowing resume spam
|
||||
// TODO: fix bug preventing the button msg to be fwd'd on bus 2
|
||||
|
||||
// 1 allows the message through
|
||||
return true;
|
||||
}
|
||||
|
||||
static int chrysler_tx_lin_hook(int lin_num, uint8_t *data, int len) {
|
||||
// LIN is not used.
|
||||
return false;
|
||||
}
|
||||
|
||||
static void chrysler_init(int16_t param) {
|
||||
controls_allowed = 0;
|
||||
}
|
||||
|
||||
static int chrysler_fwd_hook(int bus_num, CAN_FIFOMailBox_TypeDef *to_fwd) {
|
||||
return -1;
|
||||
}
|
||||
|
||||
const safety_hooks chrysler_hooks = {
|
||||
.init = chrysler_init,
|
||||
.init = nooutput_init,
|
||||
.rx = chrysler_rx_hook,
|
||||
.tx = chrysler_tx_hook,
|
||||
.tx_lin = chrysler_tx_lin_hook,
|
||||
.tx_lin = nooutput_tx_lin_hook,
|
||||
.ignition = default_ign_hook,
|
||||
.fwd = chrysler_fwd_hook,
|
||||
.fwd = nooutput_fwd_hook,
|
||||
};
|
||||
|
||||
|
||||
@@ -258,7 +258,7 @@ static int tesla_fwd_hook(int bus_num, CAN_FIFOMailBox_TypeDef *to_fwd)
|
||||
// remove EPB_epasControl
|
||||
if (addr == 0x214)
|
||||
{
|
||||
return false;
|
||||
return -1;
|
||||
}
|
||||
|
||||
return 2; // Custom EPAS bus
|
||||
@@ -269,12 +269,12 @@ static int tesla_fwd_hook(int bus_num, CAN_FIFOMailBox_TypeDef *to_fwd)
|
||||
// remove GTW_epasControl in forwards
|
||||
if (addr == 0x101)
|
||||
{
|
||||
return false;
|
||||
return -1;
|
||||
}
|
||||
|
||||
return 0; // Chassis CAN
|
||||
}
|
||||
return false;
|
||||
return -1;
|
||||
}
|
||||
|
||||
const safety_hooks tesla_hooks = {
|
||||
|
||||
Binary file not shown.
|
Before Width: | Height: | Size: 12 KiB After Width: | Height: | Size: 4.2 KiB |
@@ -42,10 +42,13 @@ void set_toyota_torque_meas(int min, int max);
|
||||
void set_cadillac_torque_driver(int min, int max);
|
||||
void set_gm_torque_driver(int min, int max);
|
||||
void set_hyundai_torque_driver(int min, int max);
|
||||
void set_chrysler_torque_meas(int min, int max);
|
||||
void set_toyota_rt_torque_last(int t);
|
||||
void set_toyota_desired_torque_last(int t);
|
||||
int get_toyota_torque_meas_min(void);
|
||||
int get_toyota_torque_meas_max(void);
|
||||
int get_chrysler_torque_meas_min(void);
|
||||
int get_chrysler_torque_meas_max(void);
|
||||
|
||||
void init_tests_honda(void);
|
||||
int get_ego_speed(void);
|
||||
@@ -84,8 +87,9 @@ int toyota_ipas_tx_hook(CAN_FIFOMailBox_TypeDef *to_send);
|
||||
void init_tests_chrysler(void);
|
||||
void chrysler_rx_hook(CAN_FIFOMailBox_TypeDef *to_push);
|
||||
int chrysler_tx_hook(CAN_FIFOMailBox_TypeDef *to_send);
|
||||
void chrysler_init(int16_t param);
|
||||
void set_chrysler_desired_torque_last(int t);
|
||||
void set_chrysler_rt_torque_last(int t);
|
||||
|
||||
|
||||
""")
|
||||
|
||||
|
||||
+27
-5
@@ -26,6 +26,7 @@ struct sample_t toyota_torque_meas;
|
||||
struct sample_t cadillac_torque_driver;
|
||||
struct sample_t gm_torque_driver;
|
||||
struct sample_t hyundai_torque_driver;
|
||||
struct sample_t chrysler_torque_driver;
|
||||
|
||||
TIM_TypeDef timer;
|
||||
TIM_TypeDef *TIM2 = &timer;
|
||||
@@ -81,6 +82,19 @@ void set_hyundai_torque_driver(int min, int max){
|
||||
hyundai_torque_driver.max = max;
|
||||
}
|
||||
|
||||
void set_chrysler_torque_meas(int min, int max){
|
||||
chrysler_torque_meas.min = min;
|
||||
chrysler_torque_meas.max = max;
|
||||
}
|
||||
|
||||
int get_chrysler_torque_meas_min(void){
|
||||
return chrysler_torque_meas.min;
|
||||
}
|
||||
|
||||
int get_chrysler_torque_meas_max(void){
|
||||
return chrysler_torque_meas.max;
|
||||
}
|
||||
|
||||
int get_toyota_torque_meas_min(void){
|
||||
return toyota_torque_meas.min;
|
||||
}
|
||||
@@ -105,6 +119,10 @@ void set_hyundai_rt_torque_last(int t){
|
||||
hyundai_rt_torque_last = t;
|
||||
}
|
||||
|
||||
void set_chrysler_rt_torque_last(int t){
|
||||
chrysler_rt_torque_last = t;
|
||||
}
|
||||
|
||||
void set_toyota_desired_torque_last(int t){
|
||||
toyota_desired_torque_last = t;
|
||||
}
|
||||
@@ -181,6 +199,15 @@ void init_tests_hyundai(void){
|
||||
set_timer(0);
|
||||
}
|
||||
|
||||
void init_tests_chrysler(void){
|
||||
chrysler_torque_driver.min = 0;
|
||||
chrysler_torque_driver.max = 0;
|
||||
chrysler_desired_torque_last = 0;
|
||||
chrysler_rt_torque_last = 0;
|
||||
chrysler_ts_last = 0;
|
||||
set_timer(0);
|
||||
}
|
||||
|
||||
void init_tests_honda(void){
|
||||
ego_speed = 0;
|
||||
gas_interceptor_detected = 0;
|
||||
@@ -188,11 +215,6 @@ void init_tests_honda(void){
|
||||
gas_prev = 0;
|
||||
}
|
||||
|
||||
void init_tests_chrysler(void){
|
||||
chrysler_desired_torque_last = 0;
|
||||
set_timer(0);
|
||||
}
|
||||
|
||||
void set_gmlan_digital_output(int to_set){
|
||||
}
|
||||
|
||||
|
||||
+139
-56
@@ -3,86 +3,169 @@ import unittest
|
||||
import numpy as np
|
||||
import libpandasafety_py
|
||||
|
||||
MAX_RATE_UP = 3
|
||||
MAX_RATE_DOWN = 3
|
||||
MAX_STEER = 261
|
||||
|
||||
MAX_RT_DELTA = 112
|
||||
RT_INTERVAL = 250000
|
||||
|
||||
MAX_TORQUE_ERROR = 80
|
||||
|
||||
def twos_comp(val, bits):
|
||||
if val >= 0:
|
||||
return val
|
||||
else:
|
||||
return (2**bits) + val
|
||||
|
||||
def sign(a):
|
||||
if a > 0:
|
||||
return 1
|
||||
else:
|
||||
return -1
|
||||
|
||||
class TestChryslerSafety(unittest.TestCase):
|
||||
@classmethod
|
||||
def setUp(cls):
|
||||
cls.safety = libpandasafety_py.libpandasafety
|
||||
cls.safety.chrysler_init(0)
|
||||
cls.safety.nooutput_init(0)
|
||||
cls.safety.init_tests_chrysler()
|
||||
|
||||
def _acc_msg(self, active):
|
||||
def _button_msg(self, buttons):
|
||||
to_send = libpandasafety_py.ffi.new('CAN_FIFOMailBox_TypeDef *')
|
||||
to_send[0].RIR = 0x1f4 << 21
|
||||
to_send[0].RDLR = 0xfe3fff1f if active else 0xfe0fff1f
|
||||
return to_send
|
||||
|
||||
|
||||
def _brake_msg(self, brake):
|
||||
to_send = libpandasafety_py.ffi.new('CAN_FIFOMailBox_TypeDef *')
|
||||
to_send[0].RIR = 0x140 << 21
|
||||
to_send[0].RDLR = 0x485 if brake else 0x480
|
||||
to_send[0].RIR = 1265 << 21
|
||||
to_send[0].RDLR = buttons
|
||||
return to_send
|
||||
|
||||
def _steer_msg(self, angle):
|
||||
def _set_prev_torque(self, t):
|
||||
self.safety.set_chrysler_desired_torque_last(t)
|
||||
self.safety.set_chrysler_rt_torque_last(t)
|
||||
self.safety.set_chrysler_torque_meas(t, t)
|
||||
|
||||
def _torque_meas_msg(self, torque):
|
||||
to_send = libpandasafety_py.ffi.new('CAN_FIFOMailBox_TypeDef *')
|
||||
to_send[0].RIR = 544 << 21
|
||||
to_send[0].RDHR = ((torque + 1024) >> 8) + (((torque + 1024) & 0xff) << 8)
|
||||
return to_send
|
||||
|
||||
def _torque_msg(self, torque):
|
||||
to_send = libpandasafety_py.ffi.new('CAN_FIFOMailBox_TypeDef *')
|
||||
to_send[0].RIR = 0x292 << 21
|
||||
c_angle = (1024 + angle)
|
||||
to_send[0].RDLR = 0x10 | ((c_angle & 0xf00) >> 8) | ((c_angle & 0xff) << 8)
|
||||
to_send[0].RDLR = ((torque + 1024) >> 8) + (((torque + 1024) & 0xff) << 8)
|
||||
return to_send
|
||||
|
||||
def test_default_controls_not_allowed(self):
|
||||
self.assertFalse(self.safety.get_controls_allowed())
|
||||
|
||||
def test_acc_enables_controls(self):
|
||||
self.safety.set_controls_allowed(0)
|
||||
self.safety.chrysler_rx_hook(self._acc_msg(0))
|
||||
self.assertFalse(self.safety.get_controls_allowed())
|
||||
self.safety.chrysler_rx_hook(self._acc_msg(1))
|
||||
self.assertTrue(self.safety.get_controls_allowed())
|
||||
self.safety.chrysler_rx_hook(self._acc_msg(0))
|
||||
self.assertFalse(self.safety.get_controls_allowed())
|
||||
def test_steer_safety_check(self):
|
||||
for enabled in [0, 1]:
|
||||
for t in range(-MAX_STEER*2, MAX_STEER*2):
|
||||
self.safety.set_controls_allowed(enabled)
|
||||
self._set_prev_torque(t)
|
||||
if abs(t) > MAX_STEER or (not enabled and abs(t) > 0):
|
||||
self.assertFalse(self.safety.chrysler_tx_hook(self._torque_msg(t)))
|
||||
else:
|
||||
self.assertTrue(self.safety.chrysler_tx_hook(self._torque_msg(t)))
|
||||
|
||||
def test_disengage_on_brake(self):
|
||||
def test_manually_enable_controls_allowed(self):
|
||||
self.safety.set_controls_allowed(1)
|
||||
self.safety.chrysler_rx_hook(self._brake_msg(0))
|
||||
self.assertTrue(self.safety.get_controls_allowed())
|
||||
self.safety.chrysler_rx_hook(self._brake_msg(1))
|
||||
self.safety.set_controls_allowed(0)
|
||||
self.assertFalse(self.safety.get_controls_allowed())
|
||||
|
||||
def test_steer_calculation(self):
|
||||
self.assertEqual(0x14, self._steer_msg(0)[0].RDLR) # straight, no steering
|
||||
def test_enable_control_allowed_from_cruise(self):
|
||||
to_push = libpandasafety_py.ffi.new('CAN_FIFOMailBox_TypeDef *')
|
||||
to_push[0].RIR = 0x1f4 << 21
|
||||
to_push[0].RDLR = 0x380000
|
||||
|
||||
self.safety.chrysler_rx_hook(to_push)
|
||||
self.assertTrue(self.safety.get_controls_allowed())
|
||||
|
||||
def test_disable_control_allowed_from_cruise(self):
|
||||
to_push = libpandasafety_py.ffi.new('CAN_FIFOMailBox_TypeDef *')
|
||||
to_push[0].RIR = 0x1f4 << 21
|
||||
to_push[0].RDLR = 0
|
||||
|
||||
def test_steer_tx(self):
|
||||
self.safety.set_controls_allowed(1)
|
||||
self.assertTrue(self.safety.chrysler_tx_hook(self._steer_msg(0)))
|
||||
self.safety.set_chrysler_desired_torque_last(227)
|
||||
self.assertTrue(self.safety.chrysler_tx_hook(self._steer_msg(230)))
|
||||
self.assertFalse(self.safety.chrysler_tx_hook(self._steer_msg(231)))
|
||||
self.safety.set_chrysler_desired_torque_last(-227)
|
||||
self.assertFalse(self.safety.chrysler_tx_hook(self._steer_msg(-231)))
|
||||
self.assertTrue(self.safety.chrysler_tx_hook(self._steer_msg(-230)))
|
||||
# verify max change
|
||||
self.safety.set_chrysler_desired_torque_last(0)
|
||||
self.assertFalse(self.safety.chrysler_tx_hook(self._steer_msg(230)))
|
||||
|
||||
self.safety.set_controls_allowed(0)
|
||||
self.safety.set_chrysler_desired_torque_last(0)
|
||||
self.assertFalse(self.safety.chrysler_tx_hook(self._steer_msg(3)))
|
||||
self.assertTrue(self.safety.chrysler_tx_hook(self._steer_msg(0)))
|
||||
# verify when controls not allowed we can still go back towards 0
|
||||
self.safety.set_chrysler_desired_torque_last(10)
|
||||
self.assertFalse(self.safety.chrysler_tx_hook(self._steer_msg(10)))
|
||||
self.assertFalse(self.safety.chrysler_tx_hook(self._steer_msg(11)))
|
||||
self.assertTrue(self.safety.chrysler_tx_hook(self._steer_msg(7)))
|
||||
self.assertTrue(self.safety.chrysler_tx_hook(self._steer_msg(4)))
|
||||
self.assertTrue(self.safety.chrysler_tx_hook(self._steer_msg(0)))
|
||||
self.safety.set_chrysler_desired_torque_last(-10)
|
||||
self.assertFalse(self.safety.chrysler_tx_hook(self._steer_msg(-10)))
|
||||
self.assertFalse(self.safety.chrysler_tx_hook(self._steer_msg(-11)))
|
||||
self.assertTrue(self.safety.chrysler_tx_hook(self._steer_msg(-7)))
|
||||
self.assertTrue(self.safety.chrysler_tx_hook(self._steer_msg(-4)))
|
||||
self.assertTrue(self.safety.chrysler_tx_hook(self._steer_msg(0)))
|
||||
self.safety.chrysler_rx_hook(to_push)
|
||||
self.assertFalse(self.safety.get_controls_allowed())
|
||||
|
||||
def test_non_realtime_limit_up(self):
|
||||
self.safety.set_controls_allowed(True)
|
||||
|
||||
self._set_prev_torque(0)
|
||||
self.assertTrue(self.safety.chrysler_tx_hook(self._torque_msg(MAX_RATE_UP)))
|
||||
|
||||
self._set_prev_torque(0)
|
||||
self.assertFalse(self.safety.chrysler_tx_hook(self._torque_msg(MAX_RATE_UP + 1)))
|
||||
|
||||
def test_non_realtime_limit_down(self):
|
||||
self.safety.set_controls_allowed(True)
|
||||
|
||||
self.safety.set_chrysler_rt_torque_last(MAX_STEER)
|
||||
torque_meas = MAX_STEER - MAX_TORQUE_ERROR - 20
|
||||
self.safety.set_chrysler_torque_meas(torque_meas, torque_meas)
|
||||
self.safety.set_chrysler_desired_torque_last(MAX_STEER)
|
||||
self.assertTrue(self.safety.chrysler_tx_hook(self._torque_msg(MAX_STEER - MAX_RATE_DOWN)))
|
||||
|
||||
self.safety.set_chrysler_rt_torque_last(MAX_STEER)
|
||||
self.safety.set_chrysler_torque_meas(torque_meas, torque_meas)
|
||||
self.safety.set_chrysler_desired_torque_last(MAX_STEER)
|
||||
self.assertFalse(self.safety.chrysler_tx_hook(self._torque_msg(MAX_STEER - MAX_RATE_DOWN + 1)))
|
||||
|
||||
def test_exceed_torque_sensor(self):
|
||||
self.safety.set_controls_allowed(True)
|
||||
|
||||
for sign in [-1, 1]:
|
||||
self._set_prev_torque(0)
|
||||
for t in np.arange(0, MAX_TORQUE_ERROR + 2, 2): # step needs to be smaller than MAX_TORQUE_ERROR
|
||||
t *= sign
|
||||
self.assertTrue(self.safety.chrysler_tx_hook(self._torque_msg(t)))
|
||||
|
||||
self.assertFalse(self.safety.chrysler_tx_hook(self._torque_msg(sign * (MAX_TORQUE_ERROR + 2))))
|
||||
|
||||
def test_realtime_limit_up(self):
|
||||
self.safety.set_controls_allowed(True)
|
||||
|
||||
for sign in [-1, 1]:
|
||||
self.safety.init_tests_chrysler()
|
||||
self._set_prev_torque(0)
|
||||
for t in np.arange(0, MAX_RT_DELTA+1, 1):
|
||||
t *= sign
|
||||
self.safety.set_chrysler_torque_meas(t, t)
|
||||
self.assertTrue(self.safety.chrysler_tx_hook(self._torque_msg(t)))
|
||||
self.assertFalse(self.safety.chrysler_tx_hook(self._torque_msg(sign * (MAX_RT_DELTA + 1))))
|
||||
|
||||
self._set_prev_torque(0)
|
||||
for t in np.arange(0, MAX_RT_DELTA+1, 1):
|
||||
t *= sign
|
||||
self.safety.set_chrysler_torque_meas(t, t)
|
||||
self.assertTrue(self.safety.chrysler_tx_hook(self._torque_msg(t)))
|
||||
|
||||
# Increase timer to update rt_torque_last
|
||||
self.safety.set_timer(RT_INTERVAL + 1)
|
||||
self.assertTrue(self.safety.chrysler_tx_hook(self._torque_msg(sign * MAX_RT_DELTA)))
|
||||
self.assertTrue(self.safety.chrysler_tx_hook(self._torque_msg(sign * (MAX_RT_DELTA + 1))))
|
||||
|
||||
def test_torque_measurements(self):
|
||||
self.safety.chrysler_rx_hook(self._torque_meas_msg(50))
|
||||
self.safety.chrysler_rx_hook(self._torque_meas_msg(-50))
|
||||
self.safety.chrysler_rx_hook(self._torque_meas_msg(0))
|
||||
self.safety.chrysler_rx_hook(self._torque_meas_msg(0))
|
||||
self.safety.chrysler_rx_hook(self._torque_meas_msg(0))
|
||||
self.safety.chrysler_rx_hook(self._torque_meas_msg(0))
|
||||
|
||||
self.assertEqual(-50, self.safety.get_chrysler_torque_meas_min())
|
||||
self.assertEqual(50, self.safety.get_chrysler_torque_meas_max())
|
||||
|
||||
self.safety.chrysler_rx_hook(self._torque_meas_msg(0))
|
||||
self.assertEqual(0, self.safety.get_chrysler_torque_meas_max())
|
||||
self.assertEqual(-50, self.safety.get_chrysler_torque_meas_min())
|
||||
|
||||
self.safety.chrysler_rx_hook(self._torque_meas_msg(0))
|
||||
self.assertEqual(0, self.safety.get_chrysler_torque_meas_max())
|
||||
self.assertEqual(0, self.safety.get_chrysler_torque_meas_min())
|
||||
|
||||
|
||||
if __name__ == "__main__":
|
||||
unittest.main()
|
||||
|
||||
Reference in New Issue
Block a user