2016-09-26 09:44:21 -07:00
/*
Speeduino - Simple engine management for the Arduino Mega 2560 platform
Copyright ( C ) Josh Stewart
A full copy of the license may be found in the projects root directory
can_comms was originally contributed by Darren Siepka
*/
/*
can_command is called when a command is received over serial3 from the Can interface
It parses the command and calls the relevant function
sendcancommand is called when a comman d is to be sent via serial3 to the Can interface
*/
//#include "cancomms.h"
//#include "globals.h"
//#include "storage.h"
2017-02-07 20:40:44 -08:00
# if defined(__AVR_ATmega1280__) || defined(__AVR_ATmega2560__) || defined(__AVR_ATmega2561__)
2016-09-30 08:57:57 -07:00
void canCommand ( )
2016-09-26 09:44:21 -07:00
{
switch ( Serial3 . read ( ) )
{
2016-09-29 04:40:16 -07:00
case ' A ' : // sends the bytes of realtime values
2017-04-22 06:31:13 -07:00
sendValues ( 0 , packetSize , 3 ) ; //send values to serial3
2016-09-29 04:40:16 -07:00
break ;
2016-09-26 09:44:21 -07:00
case ' G ' : // this is the reply command sent by the Can interface
2017-01-10 23:30:46 -08:00
//uint8_t Gdata;
2016-09-26 09:44:21 -07:00
while ( Serial3 . available ( ) = = 0 ) { }
cancmdfail = Serial3 . read ( ) ;
2017-04-08 16:48:39 -07:00
if ( cancmdfail ! = 0 )
2017-01-10 23:30:46 -08:00
{
2017-04-08 16:48:39 -07:00
for ( byte Gx = 0 ; Gx < 8 ; Gx + + ) //read all 8 bytes of data
{
while ( Serial3 . available ( ) = = 0 ) { }
Gdata [ Gx ] = Serial3 . read ( ) ;
}
Glow = Gdata [ ( configPage10 . caninput_param_start_byte [ currentStatus . current_caninchannel ] ) ] ;
if ( configPage10 . caninput_param_num_bytes [ currentStatus . current_caninchannel ] = = 2 )
{
if ( ( configPage10 . caninput_param_start_byte [ currentStatus . current_caninchannel ] ) ! = 7 ) //you cant have a 2 byte value starting at byte 7(8 on the list)
{
Ghigh = Gdata [ ( ( configPage10 . caninput_param_start_byte [ currentStatus . current_caninchannel ] ) + 1 ) ] ;
}
}
else
{
Ghigh = 0 ;
}
currentStatus . canin [ currentStatus . current_caninchannel ] = word ( Ghigh , Glow ) ;
2017-01-10 23:30:46 -08:00
}
2017-04-08 16:48:39 -07:00
else { } //continue as command request failed and/or data/device was not available
if ( currentStatus . current_caninchannel < = 6 ) // if channel is 0-7
{
currentStatus . current_caninchannel + + ; //inc to next channel
}
else
{
currentStatus . current_caninchannel = 0 ; //reset to start
}
2016-09-29 04:40:16 -07:00
break ;
2016-09-26 09:44:21 -07:00
2016-09-29 04:40:16 -07:00
case ' L ' :
uint8_t Llength ;
2016-09-26 09:44:21 -07:00
while ( Serial3 . available ( ) = = 0 ) { }
canlisten = Serial3 . read ( ) ;
if ( canlisten = = 0 )
{
//command request failed and/or data/device was not available
break ;
}
while ( Serial3 . available ( ) = = 0 ) { }
Llength = Serial3 . read ( ) ; // next the number of bytes expected value
for ( uint8_t Lcount = 0 ; Lcount < Llength ; Lcount + + )
2017-02-07 20:40:44 -08:00
{
while ( Serial3 . available ( ) = = 0 ) { }
2016-09-26 09:44:21 -07:00
// receive all x bytes into "Lbuffer"
Lbuffer [ Lcount ] = Serial3 . read ( ) ;
}
2017-02-07 20:40:44 -08:00
break ;
2017-05-08 15:15:03 -07:00
case ' r ' : //New format for the optimised OutputChannels
// cmdPending = true;
byte cmd ;
if ( Serial . available ( ) < 6 ) { return ; }
Serial . read ( ) ; //Read the $tsCanId
cmd = Serial . read ( ) ;
2017-02-07 20:40:44 -08:00
2017-05-08 15:15:03 -07:00
uint16_t offset , length ;
if ( cmd = = 0x30 ) //Send output channels command 0x30 is 48dec
{
byte tmp ;
tmp = Serial . read ( ) ;
offset = word ( Serial . read ( ) , tmp ) ;
tmp = Serial . read ( ) ;
length = word ( Serial . read ( ) , tmp ) ;
sendValues ( offset , length , 3 ) ;
}
else
{
//No other r/ commands should be called
}
cmdPending = false ;
break ;
2016-09-26 09:44:21 -07:00
case ' S ' : // send code version
2016-09-29 04:40:16 -07:00
for ( unsigned int sig = 0 ; sig < sizeof ( displaySignature ) - 1 ; sig + + ) {
2017-02-07 20:40:44 -08:00
Serial3 . write ( displaySignature [ sig ] ) ;
2016-09-29 04:40:16 -07:00
}
//Serial3.print("speeduino 201609-dev");
break ;
2016-09-26 09:44:21 -07:00
case ' Q ' : // send code version
2016-09-29 04:40:16 -07:00
for ( unsigned int revn = 0 ; revn < sizeof ( TSfirmwareVersion ) - 1 ; revn + + ) {
Serial3 . write ( TSfirmwareVersion [ revn ] ) ;
}
//Serial3.print("speeduino 201609-dev");
break ;
2016-09-26 09:44:21 -07:00
default :
2016-09-29 04:40:16 -07:00
break ;
2016-09-26 09:44:21 -07:00
}
}
2017-05-08 15:15:03 -07:00
// this routine sends a request(either "0" for a "G" , "1" for a "L" , "2" for a "R" to the Can interface or "3" sends the request via the actual local canbus
2017-04-08 16:48:39 -07:00
void sendCancommand ( uint8_t cmdtype , uint16_t canaddress , uint8_t candata1 , uint8_t candata2 , uint16_t paramgroup )
2016-09-26 09:44:21 -07:00
{
switch ( cmdtype )
{
case 0 :
Serial3 . print ( " G " ) ;
Serial3 . write ( canaddress ) ; //tscanid of speeduino device
Serial3 . write ( candata1 ) ; // table id
Serial3 . write ( candata2 ) ; //table memory offset
break ;
2017-02-07 20:40:44 -08:00
2016-09-26 09:44:21 -07:00
case 1 : //send request to listen for a can message
Serial3 . print ( " L " ) ;
Serial3 . write ( canaddress ) ; //11 bit canaddress of device to listen for
2017-02-07 20:40:44 -08:00
break ;
2017-04-08 16:48:39 -07:00
case 2 :
Serial3 . print ( " R " ) ;
Serial3 . write ( lowByte ( paramgroup ) ) ; //send lsb first
Serial3 . write ( lowByte ( paramgroup > > 8 ) ) ;
2017-05-08 15:15:03 -07:00
break ;
case 3 :
//send to truecan send routine
break ;
2017-02-07 20:40:44 -08:00
}
2016-09-26 09:44:21 -07:00
}
2017-02-07 20:40:44 -08:00
# else
2017-02-08 14:54:25 -08:00
//Dummy functions for those that can't do Serial3
2017-02-07 20:40:44 -08:00
void canCommand ( ) { return ; }
2017-04-08 16:48:39 -07:00
void sendCancommand ( uint8_t cmdtype , uint16_t canaddress , uint8_t candata1 , uint8_t candata2 , uint16_t paramgroup ) { return ; }
2017-02-07 20:40:44 -08:00
# endif