openpilot is an open source driver assistance system. openpilot performs the functions of Automated Lane Centering and Adaptive Cruise Control for over 200 supported car makes and models.
You can not select more than 25 topics Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.

71 lines
3.2 KiB

#pragma once
extern const uint16_t FLAG_VOLKSWAGEN_LONG_CONTROL;
const uint16_t FLAG_VOLKSWAGEN_LONG_CONTROL = 1;
static uint8_t volkswagen_crc8_lut_8h2f[256]; // Static lookup table for CRC8 poly 0x2F, aka 8H2F/AUTOSAR
extern bool volkswagen_longitudinal;
bool volkswagen_longitudinal = false;
extern bool volkswagen_set_button_prev;
bool volkswagen_set_button_prev = false;
extern bool volkswagen_resume_button_prev;
bool volkswagen_resume_button_prev = false;
#define MSG_LH_EPS_03 0x09FU // RX from EPS, for driver steering torque
#define MSG_ESP_19 0x0B2U // RX from ABS, for wheel speeds
#define MSG_ESP_05 0x106U // RX from ABS, for brake switch state
#define MSG_TSK_06 0x120U // RX from ECU, for ACC status from drivetrain coordinator
#define MSG_MOTOR_20 0x121U // RX from ECU, for driver throttle input
#define MSG_ACC_06 0x122U // TX by OP, ACC control instructions to the drivetrain coordinator
#define MSG_HCA_01 0x126U // TX by OP, Heading Control Assist steering torque
#define MSG_GRA_ACC_01 0x12BU // TX by OP, ACC control buttons for cancel/resume
#define MSG_ACC_07 0x12EU // TX by OP, ACC control instructions to the drivetrain coordinator
#define MSG_ACC_02 0x30CU // TX by OP, ACC HUD data to the instrument cluster
#define MSG_LDW_02 0x397U // TX by OP, Lane line recognition and text alerts
#define MSG_MOTOR_14 0x3BEU // RX from ECU, for brake switch status
static uint32_t volkswagen_mqb_meb_get_checksum(const CANPacket_t *msg) {
return (uint8_t)msg->data[0];
}
static uint8_t volkswagen_mqb_meb_get_counter(const CANPacket_t *msg) {
// MQB/MEB message counters are consistently found at LSB 8.
return (uint8_t)msg->data[1] & 0xFU;
}
static uint32_t volkswagen_mqb_meb_compute_crc(const CANPacket_t *msg) {
int len = GET_LEN(msg);
// This is CRC-8H2F/AUTOSAR with a twist. See the opendbc/car/volkswagen/ implementation
// of this algorithm for a version with explanatory comments.
uint8_t crc = 0xFFU;
for (int i = 1; i < len; i++) {
crc ^= (uint8_t)msg->data[i];
crc = volkswagen_crc8_lut_8h2f[crc];
}
uint8_t counter = volkswagen_mqb_meb_get_counter(msg);
if (msg->addr == MSG_LH_EPS_03) {
crc ^= (uint8_t[]){0xF5, 0xF5, 0xF5, 0xF5, 0xF5, 0xF5, 0xF5, 0xF5, 0xF5, 0xF5, 0xF5, 0xF5, 0xF5, 0xF5, 0xF5, 0xF5}[counter];
} else if (msg->addr == MSG_ESP_05) {
crc ^= (uint8_t[]){0x07, 0x07, 0x07, 0x07, 0x07, 0x07, 0x07, 0x07, 0x07, 0x07, 0x07, 0x07, 0x07, 0x07, 0x07, 0x07}[counter];
} else if (msg->addr == MSG_TSK_06) {
crc ^= (uint8_t[]){0xC4, 0xE2, 0x4F, 0xE4, 0xF8, 0x2F, 0x56, 0x81, 0x9F, 0xE5, 0x83, 0x44, 0x05, 0x3F, 0x97, 0xDF}[counter];
} else if (msg->addr == MSG_MOTOR_20) {
crc ^= (uint8_t[]){0xE9, 0x65, 0xAE, 0x6B, 0x7B, 0x35, 0xE5, 0x5F, 0x4E, 0xC7, 0x86, 0xA2, 0xBB, 0xDD, 0xEB, 0xB4}[counter];
} else if (msg->addr == MSG_GRA_ACC_01) {
crc ^= (uint8_t[]){0x6A, 0x38, 0xB4, 0x27, 0x22, 0xEF, 0xE1, 0xBB, 0xF8, 0x80, 0x84, 0x49, 0xC7, 0x9E, 0x1E, 0x2B}[counter];
} else {
// Undefined CAN message, CRC check expected to fail
}
crc = volkswagen_crc8_lut_8h2f[crc];
return (uint8_t)(crc ^ 0xFFU);
}