@ -1,32 +1,34 @@ 
			
		
	
		
			
				
					struct  sample_t  torque_meas ;            // last 3 motor torques produced by the eps
  
			
		
	
		
			
				
					int  toyota_no_dsu_car  =  0 ;                 // ch-r and camry don't have the DSU
  
			
		
	
		
			
				
					int  toyota_giraffe_switch_1  =  0 ;           // is giraffe switch 1 high?
  
			
		
	
		
			
				
					
 
			
		
	
		
			
				
					// global torque limit
  
			
		
	
		
			
				
					const  int  MAX_TORQUE  =  1500 ;        // max torque cmd allowed ever
  
			
		
	
		
			
				
					const  int  TOYOTA_ MAX_TORQUE=  1500 ;        // max torque cmd allowed ever
  
			
		
	
		
			
				
					
 
			
		
	
		
			
				
					// rate based torque limit + stay within actually applied
  
			
		
	
		
			
				
					// packet is sent at 100hz, so this limit is 1000/sec
  
			
		
	
		
			
				
					const  int  MAX_RATE_UP  =  10 ;         // ramp up slow
  
			
		
	
		
			
				
					const  int  MAX_RATE_DOWN  =  25 ;       // ramp down fast
  
			
		
	
		
			
				
					const  int  MAX_TORQUE_ERROR  =  350 ;   // max torque cmd in excess of torque motor
  
			
		
	
		
			
				
					const  int  TOYOTA_ MAX_RATE_UP=  10 ;         // ramp up slow
  
			
		
	
		
			
				
					const  int  TOYOTA_ MAX_RATE_DOWN=  25 ;       // ramp down fast
  
			
		
	
		
			
				
					const  int  TOYOTA_ MAX_TORQUE_ERROR=  350 ;   // max torque cmd in excess of torque motor
  
			
		
	
		
			
				
					
 
			
		
	
		
			
				
					// real time torque limit to prevent controls spamming
  
			
		
	
		
			
				
					// the real time limit is 1500/sec
  
			
		
	
		
			
				
					const  int  MAX_RT_DELTA  =  375 ;       // max delta torque allowed for real time checks
  
			
		
	
		
			
				
					const  int  RT_INTERVAL  =  250000 ;     // 250ms between real time checks
  
			
		
	
		
			
				
					const  int  TOYOTA_ MAX_RT_DELTA=  375 ;       // max delta torque allowed for real time checks
  
			
		
	
		
			
				
					const  int  TOYOTA_ RT_INTERVAL=  250000 ;     // 250ms between real time checks
  
			
		
	
		
			
				
					
 
			
		
	
		
			
				
					// longitudinal limits
  
			
		
	
		
			
				
					const  int  MAX_ACCEL  =  1500 ;         // 1.5 m/s2
  
			
		
	
		
			
				
					const  int  MIN_ACCEL  =  - 3000 ;        // 3.0 m/s2
  
			
		
	
		
			
				
					const  int  TOYOTA_ MAX_ACCEL=  1500 ;         // 1.5 m/s2
  
			
		
	
		
			
				
					const  int  TOYOTA_ MIN_ACCEL=  - 3000 ;        // 3.0 m/s2
  
			
		
	
		
			
				
					
 
			
		
	
		
			
				
					// global actuation limit state
  
			
		
	
		
			
				
					int  actuation_limits  =  1 ;                // by default steer limits are imposed
  
			
		
	
		
			
				
					int  dbc_eps_torque_factor  =  100 ;    // conversion factor for STEER_TORQUE_EPS in %: see dbc file
  
			
		
	
		
			
				
					int  toyota_ actuation_limits=  1 ;           // by default steer limits are imposed
  
			
		
	
		
			
				
					int  toyota_ dbc_eps_torque_factor=  100 ;    // conversion factor for STEER_TORQUE_EPS in %: see dbc file
  
			
		
	
		
			
				
					
 
			
		
	
		
			
				
					// state of torque limits
  
			
		
	
		
			
				
					int  desired_torque_last  =  0 ;        // last desired steer torque
  
			
		
	
		
			
				
					int  rt_torque_last  =  0 ;             // last desired torque for real time check
  
			
		
	
		
			
				
					uint32_t  ts_last  =  0 ;  
			
		
	
		
			
				
					int  cruise_engaged_last  =  0 ;            // cruise state
  
			
		
	
		
			
				
					int  toyota_desired_torque_last  =  0 ;        // last desired steer torque
  
			
		
	
		
			
				
					int  toyota_rt_torque_last  =  0 ;             // last desired torque for real time check
  
			
		
	
		
			
				
					uint32_t  toyota_ts_last  =  0 ;  
			
		
	
		
			
				
					int  toyota_cruise_engaged_last  =  0 ;        // cruise state
  
			
		
	
		
			
				
					struct  sample_t  toyota_torque_meas ;        // last 3 motor torques produced by the eps
  
			
		
	
		
			
				
					
 
			
		
	
		
			
				
					
 
			
		
	
		
			
				
					static  void  toyota_rx_hook ( CAN_FIFOMailBox_TypeDef  * to_push )  {  
			
		
	
	
		
			
				
					
						
						
						
							
								 
						
					 
				
				@ -36,26 +38,38 @@ static void toyota_rx_hook(CAN_FIFOMailBox_TypeDef *to_push) { 
			
		
	
		
			
				
					    torque_meas_new  =  to_signed ( torque_meas_new ,  16 ) ;   
			
		
	
		
			
				
					
 
			
		
	
		
			
				
					    // scale by dbc_factor
   
			
		
	
		
			
				
					    torque_meas_new  =  ( torque_meas_new  *  dbc_eps_torque_factor )  /  100 ;   
			
		
	
		
			
				
					    torque_meas_new  =  ( torque_meas_new  *  toyota_ dbc_eps_torque_factor)  /  100 ;   
			
		
	
		
			
				
					
 
			
		
	
		
			
				
					    // increase torque_meas by 1 to be conservative on rounding
   
			
		
	
		
			
				
					    torque_meas_new  + =  ( torque_meas_new  >  0  ?  1  :  - 1 ) ;   
			
		
	
		
			
				
					
 
			
		
	
		
			
				
					    // update array of sample
   
			
		
	
		
			
				
					    update_sample ( & torque_meas ,  torque_meas_new ) ;   
			
		
	
		
			
				
					    update_sample ( & toyota_to rque_meas ,  torque_meas_new ) ;   
			
		
	
		
			
				
					  }   
			
		
	
		
			
				
					
 
			
		
	
		
			
				
					  // enter controls on rising edge of ACC, exit controls on ACC off
   
			
		
	
		
			
				
					  if  ( ( to_push - > RIR > > 21 )  = =  0x1D2 )  {   
			
		
	
		
			
				
					    // 4 bits: 55-52
   
			
		
	
		
			
				
					    int  cruise_engaged  =  to_push - > RDHR  &  0xF00000 ;   
			
		
	
		
			
				
					    if  ( cruise_engaged  & &  ! cruise_engaged_last )  {   
			
		
	
		
			
				
					    if  ( cruise_engaged  & &  ! toyota_ cruise_engaged_last)  {   
			
		
	
		
			
				
					      controls_allowed  =  1 ;   
			
		
	
		
			
				
					    }  else  if  ( ! cruise_engaged )  {   
			
		
	
		
			
				
					      controls_allowed  =  0 ;   
			
		
	
		
			
				
					    }   
			
		
	
		
			
				
					    cruise_engaged_last  =  cruise_engaged ;   
			
		
	
		
			
				
					    toyota_ cruise_engaged_last=  cruise_engaged ;   
			
		
	
		
			
				
					  }   
			
		
	
		
			
				
					
 
			
		
	
		
			
				
					  int  bus  =  ( to_push - > RDTR  > >  4 )  &  0xF ;   
			
		
	
		
			
				
					  // 0x680 is a radar msg only found in dsu-less cars
   
			
		
	
		
			
				
					  if  ( ( to_push - > RIR > > 21 )  = =  0x680  & &  ( bus  = =  1 ) )  {   
			
		
	
		
			
				
					    toyota_no_dsu_car  =  1 ;   
			
		
	
		
			
				
					  }   
			
		
	
		
			
				
					
 
			
		
	
		
			
				
					  // 0x2E4 is lkas cmd. If it is on bus 0, then giraffe switch 1 is high
   
			
		
	
		
			
				
					  if  ( ( to_push - > RIR > > 21 )  = =  0x2E4  & &  ( bus  = =  0 ) )  {   
			
		
	
		
			
				
					    toyota_giraffe_switch_1  =  1 ;   
			
		
	
		
			
				
					  }   
			
		
	
		
			
				
					
 
			
		
	
		
			
				
					}  
			
		
	
		
			
				
					
 
			
		
	
		
			
				
					static  int  toyota_tx_hook ( CAN_FIFOMailBox_TypeDef  * to_send )  {  
			
		
	
	
		
			
				
					
						
						
						
							
								 
						
					 
				
				@ -70,8 +84,8 @@ static int toyota_tx_hook(CAN_FIFOMailBox_TypeDef *to_send) { 
			
		
	
		
			
				
					    if  ( ( to_send - > RIR > > 21 )  = =  0x343 )  {   
			
		
	
		
			
				
					      int  desired_accel  =  ( ( to_send - > RDLR  &  0xFF )  < <  8 )  |  ( ( to_send - > RDLR  > >  8 )  &  0xFF ) ;   
			
		
	
		
			
				
					      desired_accel  =  to_signed ( desired_accel ,  16 ) ;   
			
		
	
		
			
				
					      if  ( controls_allowed  & &  actuation_limits )  {   
			
		
	
		
			
				
					        int  violation  =  max_limit_check ( desired_accel ,  MAX_ACCEL ,  MIN_ACCEL ) ;   
			
		
	
		
			
				
					      if  ( controls_allowed  & &  toyota_ actuation_limits)  {   
			
		
	
		
			
				
					        int  violation  =  max_limit_check ( desired_accel ,  TOYOTA_ MAX_ACCEL,  TOYOTA_ MIN_ACCEL) ;   
			
		
	
		
			
				
					        if  ( violation )  return  0 ;   
			
		
	
		
			
				
					      }  else  if  ( ! controls_allowed  & &  ( desired_accel  ! =  0 ) )  {   
			
		
	
		
			
				
					        return  0 ;   
			
		
	
	
		
			
				
					
						
						
						
							
								 
						
					 
				
				@ -87,25 +101,26 @@ static int toyota_tx_hook(CAN_FIFOMailBox_TypeDef *to_send) { 
			
		
	
		
			
				
					      uint32_t  ts  =  TIM2 - > CNT ;   
			
		
	
		
			
				
					
 
			
		
	
		
			
				
					      // only check if controls are allowed and actuation_limits are imposed
   
			
		
	
		
			
				
					      if  ( controls_allowed  & &  actuation_limits )  {   
			
		
	
		
			
				
					      if  ( controls_allowed  & &  toyota_ actuation_limits)  {   
			
		
	
		
			
				
					
 
			
		
	
		
			
				
					        // *** global torque limit check ***
   
			
		
	
		
			
				
					        violation  | =  max_limit_check ( desired_torque ,  MAX_TORQUE ,  - MAX_TORQUE ) ;   
			
		
	
		
			
				
					        violation  | =  max_limit_check ( desired_torque ,  TOYOTA_ MAX_TORQUE,  - TOYOTA_ MAX_TORQUE) ;   
			
		
	
		
			
				
					
 
			
		
	
		
			
				
					        // *** torque rate limit check ***
   
			
		
	
		
			
				
					        violation  | =  dist_to_meas_check ( desired_torque ,  desired_torque_last ,  & torque_meas ,  MAX_RATE_UP ,  MAX_RATE_DOWN ,  MAX_TORQUE_ERROR ) ;   
			
		
	
		
			
				
					        violation  | =  dist_to_meas_check ( desired_torque ,  toyota_desired_torque_last ,  
  
			
		
	
		
			
				
					          & toyota_torque_meas ,  TOYOTA_MAX_RATE_UP ,  TOYOTA_MAX_RATE_DOWN ,  TOYOTA_MAX_TORQUE_ERROR ) ;   
			
		
	
		
			
				
					
 
			
		
	
		
			
				
					        // used next time
   
			
		
	
		
			
				
					        desired_torque_last  =  desired_torque ;   
			
		
	
		
			
				
					        toyota_ desired_torque_last=  desired_torque ;   
			
		
	
		
			
				
					
 
			
		
	
		
			
				
					        // *** torque real time rate limit check ***
   
			
		
	
		
			
				
					        violation  | =  rt_rate_limit_check ( desired_torque ,  rt_torque_last ,  MAX_RT_DELTA ) ;   
			
		
	
		
			
				
					        violation  | =  rt_rate_limit_check ( desired_torque ,  toyota_ rt_torque_last,  TOYOTA_ MAX_RT_DELTA) ;   
			
		
	
		
			
				
					
 
			
		
	
		
			
				
					        // every RT_INTERVAL set the new limits
   
			
		
	
		
			
				
					        uint32_t  ts_elapsed  =  get_ts_elapsed ( ts ,  ts_last ) ;   
			
		
	
		
			
				
					        if  ( ts_elapsed  >  RT_INTERVAL )  {   
			
		
	
		
			
				
					          rt_torque_last  =  desired_torque ;   
			
		
	
		
			
				
					          ts_last  =  ts ;   
			
		
	
		
			
				
					        uint32_t  ts_elapsed  =  get_ts_elapsed ( ts ,  toyota_t s_last ) ;   
			
		
	
		
			
				
					        if  ( ts_elapsed  >  TOYOTA_ RT_INTERVAL)  {   
			
		
	
		
			
				
					          toyota_ rt_torque_last=  desired_torque ;   
			
		
	
		
			
				
					          toyota_t s_last  =  ts ;   
			
		
	
		
			
				
					        }   
			
		
	
		
			
				
					      }   
			
		
	
		
			
				
					      
  
			
		
	
	
		
			
				
					
						
						
						
							
								 
						
					 
				
				@ -116,9 +131,9 @@ static int toyota_tx_hook(CAN_FIFOMailBox_TypeDef *to_send) { 
			
		
	
		
			
				
					
 
			
		
	
		
			
				
					      // reset to 0 if either controls is not allowed or there's a violation
   
			
		
	
		
			
				
					      if  ( violation  | |  ! controls_allowed )  {   
			
		
	
		
			
				
					        desired_torque_last  =  0 ;   
			
		
	
		
			
				
					        rt_torque_last  =  0 ;   
			
		
	
		
			
				
					        ts_last  =  ts ;   
			
		
	
		
			
				
					        toyota_ desired_torque_last=  0 ;   
			
		
	
		
			
				
					        toyota_ rt_torque_last=  0 ;   
			
		
	
		
			
				
					        toyota_t s_last  =  ts ;   
			
		
	
		
			
				
					      }   
			
		
	
		
			
				
					
 
			
		
	
		
			
				
					      if  ( violation )  {   
			
		
	
	
		
			
				
					
						
						
						
							
								 
						
					 
				
				@ -138,11 +153,19 @@ static int toyota_tx_lin_hook(int lin_num, uint8_t *data, int len) { 
			
		
	
		
			
				
					
 
			
		
	
		
			
				
					static  void  toyota_init ( int16_t  param )  {  
			
		
	
		
			
				
					  controls_allowed  =  0 ;   
			
		
	
		
			
				
					  actuation_limits  =  1 ;   
			
		
	
		
			
				
					  dbc_eps_torque_factor  =  param ;   
			
		
	
		
			
				
					  toyota_actuation_limits  =  1 ;   
			
		
	
		
			
				
					  toyota_giraffe_switch_1  =  0 ;   
			
		
	
		
			
				
					  toyota_dbc_eps_torque_factor  =  param ;   
			
		
	
		
			
				
					}  
			
		
	
		
			
				
					
 
			
		
	
		
			
				
					static  int  toyota_fwd_hook ( int  bus_num ,  CAN_FIFOMailBox_TypeDef  * to_fwd )  {  
			
		
	
		
			
				
					
 
			
		
	
		
			
				
					  // forward cam to radar and viceversa if car is dsu-less, except lkas cmd and hud
   
			
		
	
		
			
				
					  if  ( ( bus_num  = =  0  | |  bus_num  = =  2 )  & &  toyota_no_dsu_car  & &  ! toyota_giraffe_switch_1 )  {   
			
		
	
		
			
				
					    int  addr  =  to_fwd - > RIR > > 21 ;   
			
		
	
		
			
				
					    bool  is_lkas_msg  =  ( addr  = =  0x2E4  | |  addr  = =  0x412 )  & &  bus_num  = =  2 ;   
			
		
	
		
			
				
					    return  is_lkas_msg ?  - 1  :  ( uint8_t ) ( ~ bus_num  &  0x2 ) ;   
			
		
	
		
			
				
					  }   
			
		
	
		
			
				
					  return  - 1 ;   
			
		
	
		
			
				
					}  
			
		
	
		
			
				
					
 
			
		
	
	
		
			
				
					
						
						
						
							
								 
						
					 
				
				@ -157,8 +180,9 @@ const safety_hooks toyota_hooks = { 
			
		
	
		
			
				
					
 
			
		
	
		
			
				
					static  void  toyota_nolimits_init ( int16_t  param )  {  
			
		
	
		
			
				
					  controls_allowed  =  0 ;   
			
		
	
		
			
				
					  actuation_limits  =  0 ;   
			
		
	
		
			
				
					  dbc_eps_torque_factor  =  param ;   
			
		
	
		
			
				
					  toyota_actuation_limits  =  0 ;   
			
		
	
		
			
				
					  toyota_giraffe_switch_1  =  0 ;   
			
		
	
		
			
				
					  toyota_dbc_eps_torque_factor  =  param ;   
			
		
	
		
			
				
					}  
			
		
	
		
			
				
					
 
			
		
	
		
			
				
					const  safety_hooks  toyota_nolimits_hooks  =  {