📄 can.c
字号:
* Return : None
*******************************************************************************/
static void Send_UCAN_StatusMessage(u16 appl_func, char *appl_name, char *ctrl_name)
{
int i;
u8 len = 0; // Data length
u8 data[42]; // Data buffer, size 2 + 20 + 20
data[len++] = (u8)(appl_func); // Application functionality
data[len++] = (u8)(appl_func>>8);
for (i=0; i < 20; i++)
{
data[len++] = (u8) *appl_name; // Application name
if (*appl_name)
appl_name++;
}
for (i=0; i < 20; i++)
{
data[len++] = (u8) *ctrl_name; // Controller name
if (*ctrl_name)
ctrl_name++;
}
Send_UCAN_frame (CAN_ID_STATUS, data, len);
}
/*******************************************************************************
* Function Name : Message_to_UART
* Description : Send UCAN message
* Input : None
* Output : None
* Return : None
*******************************************************************************/
static void Message_to_UART(CanRxMsg *CanMsg)
{
int i;
u32 id; // CAN ID
u8 len = 0; // Data length
u8 data[16]; // Data buffer, size max 4 (id) + 8 (DLC) + 2 (time)
id = CanMsg->StdId; // Std ID 11-bit (StdId ranges from 0 to 0x7FF)
if (CanMsg->IDE == CAN_ID_EXT)
{
id |= (CanMsg->ExtId << 11); // Ext ID 29-bit (ExtId ranges from 0 to 0x3FFFF)
id |= CAN_CANSPY_INFOMASK_EXTENDED; // Set extended ID flag
}
if(CanMsg->RTR !=0)
{
id |= CAN_CANSPY_INFOMASK_REMOTEREQUEST;
}
data[len++] = (u8)(id); // CAN ID
data[len++] = (u8)(id>>8);
data[len++] = (u8)(id>>16);
data[len++] = (u8)(id>>24);
data[len++] = (u8)CanMsg->DLC; // Frame length
for (i=0; i < CanMsg->DLC; i++)
{
data[len++] = CanMsg->Data[i];
}
data[len++] = (u8)(ucan_msg.timestamp); // UCAN timestamp
data[len++] = (u8)(ucan_msg.timestamp>>8);
Send_UCAN_frame (ucan_msg.ucan_id, data, len);
}
/*******************************************************************************
* Function Name : TimeFlDiff
* Description : Calculate elapsed time between start/end, convert to float
* Input : None
* Output : None
* Return : Elapsed time in 5/11 float format
*******************************************************************************/
u64 current_tst;
static u16 TimeFlDiff(void)
{
u16 difftime[3]={0,0,0};
u64 elapsed_time, current_time;
current_time = TIMER_ElapsedTime();
elapsed_time = current_time - CAN_StartTimerValue;
current_tst = elapsed_time;
CAN_StartTimerValue = current_time;
difftime[0] = elapsed_time & 0xffff; elapsed_time >>= 16;
difftime[1] = elapsed_time & 0xffff; elapsed_time >>= 16;
difftime[2] = elapsed_time & 0xffff; elapsed_time >>= 16;
if (elapsed_time)
{
return 0; /* Overflow */
}
return Time48_ToFloat(difftime);
}
/*******************************************************************************
* Function Name : CAN_isr
* Description : Interrupt service routine for the CAN
* Input : None
* Output : None
* Return : None
*******************************************************************************/
void CAN_isr(void)
{
static CanRxMsg RxCanMsg; /* Buffer for receive messages */
RxCanMsg.StdId=0x00;
RxCanMsg.ExtId=0x00;
RxCanMsg.IDE=0;
RxCanMsg.DLC=0;
RxCanMsg.FMI=0;
RxCanMsg.Data[0]=0x00;
RxCanMsg.Data[1]=0x00;
CAN_Receive(CAN_FIFO0, &RxCanMsg);
if ((ucan_msg.canspy_record)||(ucan_msg.can_generator))
{
ucan_msg.timestamp = TimeFlDiff();
Message_to_UART(&RxCanMsg);
}
ucan_msg.can_generator = 0;
}
/*******************************************************************************
* Function Name : RecvMsg_Status
* Description : Process incoming CAN "Status" message
* Input : None
* Output : None
* Return : None
*******************************************************************************/
void RecvMsg_Status(void)
{
Send_UCAN_StatusMessage ((CAN_STATUS_FEATURE_SPY | CAN_STATUS_FEATURE_GENERATOR),
CAN_STATUS_APPLICATION, CAN_STATUS_CONTROLLER);
}
/*******************************************************************************
* Function Name : RecvMsg_CANSpy
* Description : Process incoming CAN "CAN Spy" message
* Input : None
* Output : None
* Return : None
*******************************************************************************/
void RecvMsg_CANSpy(u8 *data)
{
ucan_msg.ucan_spy_cmd = data[3];
if (ucan_msg.ucan_spy_cmd & CAN_CANSPY_FEATURE_RECORD)
{
ucan_msg.canspy_record = 1; /* turn on CAN recording */
}
else
{
ucan_msg.canspy_record = 0; /* turn off CAN recording */
}
}
/*******************************************************************************
* Function Name : RecvMsg_CANGenerator
* Description : Process incoming CAN "CAN generator" message
* Input : None
* Output : None
* Return : None
*******************************************************************************/
void RecvMsg_CANGenerator(u8 *data)
{
static u16 i = 0;
u8 count = 0;
u32 info;
if (ucan_msg.ucan_checksum != 0)
{
// drop frame, checksum error
}
cangenerate_countdown = FALSE; // Disable CAN generator
info = ((u32) data[3]) | (((u32) data[4]) << 8) |
(((u32) data[5]) << 16) | (((u32) data[6]) << 24);
if (info & CAN_CANSPY_INFOMASK_EXTENDED)
{
ucan_msg.can_msg.IDE = CAN_ID_EXT; // Ext ID 29-bit
ucan_msg.can_msg.ExtId = (info >> 11) & 0x3ffff; // ExtId ranges from 0 to 0x3FFFF
ucan_msg.can_msg.StdId = info & 0x7ff; // StdId ranges from 0 to 0x7FF
}
else
{
ucan_msg.can_msg.StdId = CAN_ID_STD; // Std ID 11-bit
ucan_msg.can_msg.ExtId = 0; // ExtId not used
ucan_msg.can_msg.StdId = info & 0x7ff; // StdId ranges from 0 to 0x7FF
}
ucan_msg.can_msg.DLC = data[7];
ucan_msg.remoterequest = (info & CAN_CANGENERATE_INFOMASK_REMOTEREQUEST) ? 1 : 0;
ucan_msg.can_msg.RTR=CAN_RTR_DATA;
// CAN data
for (i = 0; i < 8; i++)
{
ucan_msg.can_msg.Data[i] = (i < ucan_msg.can_msg.DLC) ? data[8+i] : 0;
}
if(info & CAN_CANSPY_INFOMASK_REMOTEREQUEST)
{
ucan_msg.can_msg.RTR = 0x02;
}
if (ucan_msg.can_msg.DLC)
{
// CAN time
i = 8 + ucan_msg.can_msg.DLC;
ucan_msg.time = ((u16) data[i]) | (((u16) data[i+1]) << 8);
if (ucan_msg.time)
{
// Let timer handle all transmits, start the first transmit within 1 ms
cangenerate_repeat = ucan_msg.time; // Repeat time
cangenerate_countdown = 1; // Enable CAN generator
}
else
{
// Just transmit once
CAN_Transmit(&ucan_msg.can_msg);
}
}
}
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -