|  |  |  | @ -1,14 +1,44 @@ | 
			
		
	
		
			
				
					|  |  |  |  | import math | 
			
		
	
		
			
				
					|  |  |  |  | 
 | 
			
		
	
		
			
				
					|  |  |  |  | from common.numpy_fast import clip | 
			
		
	
		
			
				
					|  |  |  |  | from selfdrive.car.hyundai.values import HyundaiFlags | 
			
		
	
		
			
				
					|  |  |  |  | 
 | 
			
		
	
		
			
				
					|  |  |  |  | def get_e_can_bus(CP): | 
			
		
	
		
			
				
					|  |  |  |  |   # On the CAN-FD platforms, the LKAS camera is on both A-CAN and E-CAN. HDA2 cars | 
			
		
	
		
			
				
					|  |  |  |  |   # have a different harness than the HDA1 and non-HDA variants in order to split | 
			
		
	
		
			
				
					|  |  |  |  |   # a different bus, since the steering is done by different ECUs. | 
			
		
	
		
			
				
					|  |  |  |  |   return 5 if CP.flags & HyundaiFlags.CANFD_HDA2 else 4 | 
			
		
	
		
			
				
					|  |  |  |  | 
 | 
			
		
	
		
			
				
					|  |  |  |  | class CanBus: | 
			
		
	
		
			
				
					|  |  |  |  |   def __init__(self, CP, hda2=None, fingerprint=None): | 
			
		
	
		
			
				
					|  |  |  |  |     if CP is None: | 
			
		
	
		
			
				
					|  |  |  |  |       assert None not in (hda2, fingerprint) | 
			
		
	
		
			
				
					|  |  |  |  |       num = math.ceil(max([k for k, v in fingerprint.items() if len(v)], default=1) / 4) | 
			
		
	
		
			
				
					|  |  |  |  |     else: | 
			
		
	
		
			
				
					|  |  |  |  |       hda2 = CP.flags & HyundaiFlags.CANFD_HDA2.value | 
			
		
	
		
			
				
					|  |  |  |  |       num = len(CP.safetyConfigs) | 
			
		
	
		
			
				
					|  |  |  |  | 
 | 
			
		
	
		
			
				
					|  |  |  |  |     # On the CAN-FD platforms, the LKAS camera is on both A-CAN and E-CAN. HDA2 cars | 
			
		
	
		
			
				
					|  |  |  |  |     # have a different harness than the HDA1 and non-HDA variants in order to split | 
			
		
	
		
			
				
					|  |  |  |  |     # a different bus, since the steering is done by different ECUs. | 
			
		
	
		
			
				
					|  |  |  |  |     self._a, self._e = 1, 0 | 
			
		
	
		
			
				
					|  |  |  |  |     if hda2: | 
			
		
	
		
			
				
					|  |  |  |  |       self._a, self._e = 0, 1 | 
			
		
	
		
			
				
					|  |  |  |  | 
 | 
			
		
	
		
			
				
					|  |  |  |  |     offset = 4*(num - 1) | 
			
		
	
		
			
				
					|  |  |  |  |     self._a += offset | 
			
		
	
		
			
				
					|  |  |  |  |     self._e += offset | 
			
		
	
		
			
				
					|  |  |  |  |     self._cam = 2 + offset | 
			
		
	
		
			
				
					|  |  |  |  | 
 | 
			
		
	
		
			
				
					|  |  |  |  |   @property | 
			
		
	
		
			
				
					|  |  |  |  |   def ECAN(self): | 
			
		
	
		
			
				
					|  |  |  |  |     return self._e | 
			
		
	
		
			
				
					|  |  |  |  | 
 | 
			
		
	
		
			
				
					|  |  |  |  |   @property | 
			
		
	
		
			
				
					|  |  |  |  |   def ACAN(self): | 
			
		
	
		
			
				
					|  |  |  |  |     return self._a | 
			
		
	
		
			
				
					|  |  |  |  | 
 | 
			
		
	
		
			
				
					|  |  |  |  |   @property | 
			
		
	
		
			
				
					|  |  |  |  |   def CAM(self): | 
			
		
	
		
			
				
					|  |  |  |  |     return self._cam | 
			
		
	
		
			
				
					|  |  |  |  | 
 | 
			
		
	
		
			
				
					|  |  |  |  | 
 | 
			
		
	
		
			
				
					|  |  |  |  | def create_steering_messages(packer, CP, enabled, lat_active, apply_steer): | 
			
		
	
		
			
				
					|  |  |  |  | def create_steering_messages(packer, CP, CAN, enabled, lat_active, apply_steer): | 
			
		
	
		
			
				
					|  |  |  |  | 
 | 
			
		
	
		
			
				
					|  |  |  |  |   ret = [] | 
			
		
	
		
			
				
					|  |  |  |  | 
 | 
			
		
	
	
		
			
				
					|  |  |  | @ -26,45 +56,45 @@ def create_steering_messages(packer, CP, enabled, lat_active, apply_steer): | 
			
		
	
		
			
				
					|  |  |  |  | 
 | 
			
		
	
		
			
				
					|  |  |  |  |   if CP.flags & HyundaiFlags.CANFD_HDA2: | 
			
		
	
		
			
				
					|  |  |  |  |     if CP.openpilotLongitudinalControl: | 
			
		
	
		
			
				
					|  |  |  |  |       ret.append(packer.make_can_msg("LFA", 5, values)) | 
			
		
	
		
			
				
					|  |  |  |  |     ret.append(packer.make_can_msg("LKAS", 4, values)) | 
			
		
	
		
			
				
					|  |  |  |  |       ret.append(packer.make_can_msg("LFA", CAN.ECAN, values)) | 
			
		
	
		
			
				
					|  |  |  |  |     ret.append(packer.make_can_msg("LKAS", CAN.ACAN, values)) | 
			
		
	
		
			
				
					|  |  |  |  |   else: | 
			
		
	
		
			
				
					|  |  |  |  |     ret.append(packer.make_can_msg("LFA", 4, values)) | 
			
		
	
		
			
				
					|  |  |  |  |     ret.append(packer.make_can_msg("LFA", CAN.ECAN, values)) | 
			
		
	
		
			
				
					|  |  |  |  | 
 | 
			
		
	
		
			
				
					|  |  |  |  |   return ret | 
			
		
	
		
			
				
					|  |  |  |  | 
 | 
			
		
	
		
			
				
					|  |  |  |  | def create_cam_0x2a4(packer, camera_values): | 
			
		
	
		
			
				
					|  |  |  |  | def create_cam_0x2a4(packer, CAN, camera_values): | 
			
		
	
		
			
				
					|  |  |  |  |   camera_values.update({ | 
			
		
	
		
			
				
					|  |  |  |  |     "BYTE7": 0, | 
			
		
	
		
			
				
					|  |  |  |  |   }) | 
			
		
	
		
			
				
					|  |  |  |  |   return packer.make_can_msg("CAM_0x2a4", 4, camera_values) | 
			
		
	
		
			
				
					|  |  |  |  |   return packer.make_can_msg("CAM_0x2a4", CAN.ACAN, camera_values) | 
			
		
	
		
			
				
					|  |  |  |  | 
 | 
			
		
	
		
			
				
					|  |  |  |  | def create_buttons(packer, CP, cnt, btn): | 
			
		
	
		
			
				
					|  |  |  |  | def create_buttons(packer, CP, CAN, cnt, btn): | 
			
		
	
		
			
				
					|  |  |  |  |   values = { | 
			
		
	
		
			
				
					|  |  |  |  |     "COUNTER": cnt, | 
			
		
	
		
			
				
					|  |  |  |  |     "SET_ME_1": 1, | 
			
		
	
		
			
				
					|  |  |  |  |     "CRUISE_BUTTONS": btn, | 
			
		
	
		
			
				
					|  |  |  |  |   } | 
			
		
	
		
			
				
					|  |  |  |  | 
 | 
			
		
	
		
			
				
					|  |  |  |  |   bus = 5 if CP.flags & HyundaiFlags.CANFD_HDA2 else 6 | 
			
		
	
		
			
				
					|  |  |  |  |   bus = CAN.ECAN if CP.flags & HyundaiFlags.CANFD_HDA2 else CAN.CAM | 
			
		
	
		
			
				
					|  |  |  |  |   return packer.make_can_msg("CRUISE_BUTTONS", bus, values) | 
			
		
	
		
			
				
					|  |  |  |  | 
 | 
			
		
	
		
			
				
					|  |  |  |  | def create_acc_cancel(packer, CP, cruise_info_copy): | 
			
		
	
		
			
				
					|  |  |  |  | def create_acc_cancel(packer, CAN, cruise_info_copy): | 
			
		
	
		
			
				
					|  |  |  |  |   values = cruise_info_copy | 
			
		
	
		
			
				
					|  |  |  |  |   values.update({ | 
			
		
	
		
			
				
					|  |  |  |  |     "ACCMode": 4, | 
			
		
	
		
			
				
					|  |  |  |  |   }) | 
			
		
	
		
			
				
					|  |  |  |  |   return packer.make_can_msg("SCC_CONTROL", get_e_can_bus(CP), values) | 
			
		
	
		
			
				
					|  |  |  |  |   return packer.make_can_msg("SCC_CONTROL", CAN.ECAN, values) | 
			
		
	
		
			
				
					|  |  |  |  | 
 | 
			
		
	
		
			
				
					|  |  |  |  | def create_lfahda_cluster(packer, CP, enabled): | 
			
		
	
		
			
				
					|  |  |  |  | def create_lfahda_cluster(packer, CAN, enabled): | 
			
		
	
		
			
				
					|  |  |  |  |   values = { | 
			
		
	
		
			
				
					|  |  |  |  |     "HDA_ICON": 1 if enabled else 0, | 
			
		
	
		
			
				
					|  |  |  |  |     "LFA_ICON": 2 if enabled else 0, | 
			
		
	
		
			
				
					|  |  |  |  |   } | 
			
		
	
		
			
				
					|  |  |  |  |   return packer.make_can_msg("LFAHDA_CLUSTER", get_e_can_bus(CP), values) | 
			
		
	
		
			
				
					|  |  |  |  |   return packer.make_can_msg("LFAHDA_CLUSTER", CAN.ECAN, values) | 
			
		
	
		
			
				
					|  |  |  |  | 
 | 
			
		
	
		
			
				
					|  |  |  |  | 
 | 
			
		
	
		
			
				
					|  |  |  |  | def create_acc_control(packer, CP, enabled, accel_last, accel, stopping, gas_override, set_speed): | 
			
		
	
		
			
				
					|  |  |  |  | def create_acc_control(packer, CAN, enabled, accel_last, accel, stopping, gas_override, set_speed): | 
			
		
	
		
			
				
					|  |  |  |  |   jerk = 5 | 
			
		
	
		
			
				
					|  |  |  |  |   jn = jerk / 50 | 
			
		
	
		
			
				
					|  |  |  |  |   if not enabled or gas_override: | 
			
		
	
	
		
			
				
					|  |  |  | @ -92,15 +122,15 @@ def create_acc_control(packer, CP, enabled, accel_last, accel, stopping, gas_ove | 
			
		
	
		
			
				
					|  |  |  |  |     "DISTANCE_SETTING": 4, | 
			
		
	
		
			
				
					|  |  |  |  |   } | 
			
		
	
		
			
				
					|  |  |  |  | 
 | 
			
		
	
		
			
				
					|  |  |  |  |   return packer.make_can_msg("SCC_CONTROL", get_e_can_bus(CP), values) | 
			
		
	
		
			
				
					|  |  |  |  |   return packer.make_can_msg("SCC_CONTROL", CAN.ECAN, values) | 
			
		
	
		
			
				
					|  |  |  |  | 
 | 
			
		
	
		
			
				
					|  |  |  |  | 
 | 
			
		
	
		
			
				
					|  |  |  |  | def create_spas_messages(packer, frame, left_blink, right_blink): | 
			
		
	
		
			
				
					|  |  |  |  | def create_spas_messages(packer, CAN, frame, left_blink, right_blink): | 
			
		
	
		
			
				
					|  |  |  |  |   ret = [] | 
			
		
	
		
			
				
					|  |  |  |  | 
 | 
			
		
	
		
			
				
					|  |  |  |  |   values = { | 
			
		
	
		
			
				
					|  |  |  |  |   } | 
			
		
	
		
			
				
					|  |  |  |  |   ret.append(packer.make_can_msg("SPAS1", 5, values)) | 
			
		
	
		
			
				
					|  |  |  |  |   ret.append(packer.make_can_msg("SPAS1", CAN.ECAN, values)) | 
			
		
	
		
			
				
					|  |  |  |  | 
 | 
			
		
	
		
			
				
					|  |  |  |  |   blink = 0 | 
			
		
	
		
			
				
					|  |  |  |  |   if left_blink: | 
			
		
	
	
		
			
				
					|  |  |  | @ -110,12 +140,12 @@ def create_spas_messages(packer, frame, left_blink, right_blink): | 
			
		
	
		
			
				
					|  |  |  |  |   values = { | 
			
		
	
		
			
				
					|  |  |  |  |     "BLINKER_CONTROL": blink, | 
			
		
	
		
			
				
					|  |  |  |  |   } | 
			
		
	
		
			
				
					|  |  |  |  |   ret.append(packer.make_can_msg("SPAS2", 5, values)) | 
			
		
	
		
			
				
					|  |  |  |  |   ret.append(packer.make_can_msg("SPAS2", CAN.ECAN, values)) | 
			
		
	
		
			
				
					|  |  |  |  | 
 | 
			
		
	
		
			
				
					|  |  |  |  |   return ret | 
			
		
	
		
			
				
					|  |  |  |  | 
 | 
			
		
	
		
			
				
					|  |  |  |  | 
 | 
			
		
	
		
			
				
					|  |  |  |  | def create_adrv_messages(packer, frame): | 
			
		
	
		
			
				
					|  |  |  |  | def create_adrv_messages(packer, CAN, frame): | 
			
		
	
		
			
				
					|  |  |  |  |   # messages needed to car happy after disabling | 
			
		
	
		
			
				
					|  |  |  |  |   # the ADAS Driving ECU to do longitudinal control | 
			
		
	
		
			
				
					|  |  |  |  | 
 | 
			
		
	
	
		
			
				
					|  |  |  | @ -123,7 +153,7 @@ def create_adrv_messages(packer, frame): | 
			
		
	
		
			
				
					|  |  |  |  | 
 | 
			
		
	
		
			
				
					|  |  |  |  |   values = { | 
			
		
	
		
			
				
					|  |  |  |  |   } | 
			
		
	
		
			
				
					|  |  |  |  |   ret.append(packer.make_can_msg("ADRV_0x51", 4, values)) | 
			
		
	
		
			
				
					|  |  |  |  |   ret.append(packer.make_can_msg("ADRV_0x51", CAN.ACAN, values)) | 
			
		
	
		
			
				
					|  |  |  |  | 
 | 
			
		
	
		
			
				
					|  |  |  |  |   if frame % 2 == 0: | 
			
		
	
		
			
				
					|  |  |  |  |     values = { | 
			
		
	
	
		
			
				
					|  |  |  | @ -133,7 +163,7 @@ def create_adrv_messages(packer, frame): | 
			
		
	
		
			
				
					|  |  |  |  |       'SET_ME_FC': 0xfc, | 
			
		
	
		
			
				
					|  |  |  |  |       'SET_ME_9': 0x9, | 
			
		
	
		
			
				
					|  |  |  |  |     } | 
			
		
	
		
			
				
					|  |  |  |  |     ret.append(packer.make_can_msg("ADRV_0x160", 5, values)) | 
			
		
	
		
			
				
					|  |  |  |  |     ret.append(packer.make_can_msg("ADRV_0x160", CAN.ECAN, values)) | 
			
		
	
		
			
				
					|  |  |  |  | 
 | 
			
		
	
		
			
				
					|  |  |  |  |   if frame % 5 == 0: | 
			
		
	
		
			
				
					|  |  |  |  |     values = { | 
			
		
	
	
		
			
				
					|  |  |  | @ -142,25 +172,25 @@ def create_adrv_messages(packer, frame): | 
			
		
	
		
			
				
					|  |  |  |  |       'SET_ME_TMP_F': 0xf, | 
			
		
	
		
			
				
					|  |  |  |  |       'SET_ME_TMP_F_2': 0xf, | 
			
		
	
		
			
				
					|  |  |  |  |     } | 
			
		
	
		
			
				
					|  |  |  |  |     ret.append(packer.make_can_msg("ADRV_0x1ea", 5, values)) | 
			
		
	
		
			
				
					|  |  |  |  |     ret.append(packer.make_can_msg("ADRV_0x1ea", CAN.ECAN, values)) | 
			
		
	
		
			
				
					|  |  |  |  | 
 | 
			
		
	
		
			
				
					|  |  |  |  |     values = { | 
			
		
	
		
			
				
					|  |  |  |  |       'SET_ME_E1': 0xe1, | 
			
		
	
		
			
				
					|  |  |  |  |       'SET_ME_3A': 0x3a, | 
			
		
	
		
			
				
					|  |  |  |  |     } | 
			
		
	
		
			
				
					|  |  |  |  |     ret.append(packer.make_can_msg("ADRV_0x200", 5, values)) | 
			
		
	
		
			
				
					|  |  |  |  |     ret.append(packer.make_can_msg("ADRV_0x200", CAN.ECAN, values)) | 
			
		
	
		
			
				
					|  |  |  |  | 
 | 
			
		
	
		
			
				
					|  |  |  |  |   if frame % 20 == 0: | 
			
		
	
		
			
				
					|  |  |  |  |     values = { | 
			
		
	
		
			
				
					|  |  |  |  |       'SET_ME_15': 0x15, | 
			
		
	
		
			
				
					|  |  |  |  |     } | 
			
		
	
		
			
				
					|  |  |  |  |     ret.append(packer.make_can_msg("ADRV_0x345", 5, values)) | 
			
		
	
		
			
				
					|  |  |  |  |     ret.append(packer.make_can_msg("ADRV_0x345", CAN.ECAN, values)) | 
			
		
	
		
			
				
					|  |  |  |  | 
 | 
			
		
	
		
			
				
					|  |  |  |  |   if frame % 100 == 0: | 
			
		
	
		
			
				
					|  |  |  |  |     values = { | 
			
		
	
		
			
				
					|  |  |  |  |       'SET_ME_22': 0x22, | 
			
		
	
		
			
				
					|  |  |  |  |       'SET_ME_41': 0x41, | 
			
		
	
		
			
				
					|  |  |  |  |     } | 
			
		
	
		
			
				
					|  |  |  |  |     ret.append(packer.make_can_msg("ADRV_0x1da", 5, values)) | 
			
		
	
		
			
				
					|  |  |  |  |     ret.append(packer.make_can_msg("ADRV_0x1da", CAN.ECAN, values)) | 
			
		
	
		
			
				
					|  |  |  |  | 
 | 
			
		
	
		
			
				
					|  |  |  |  |   return ret | 
			
		
	
	
		
			
				
					|  |  |  | 
 |