CAN静默回环模式测试

本文章主要用于 看自己写的CAN协议代码是否正确 然后因为只有一块板子,不能通信的情况

can.h

#ifndef __CAN_H
#define __CAN_H

#include "head.h"

extern FlagStatus can0_receive_flag;
extern FlagStatus can0_error_flag;
extern can_trasnmit_message_struct transmit_message;
extern can_receive_message_struct receive_message;

void CAN0_init(void);
#endif

can.c

#include "can.h"

FlagStatus can0_receive_flag=RESET;
FlagStatus can0_error_flag=RESET;
can_trasnmit_message_struct transmit_message;
can_receive_message_struct receive_message;

void CAN0_init(void)
{
	can_parameter_struct can_parameter;
	can_filter_parameter_struct can_filter;
	
	//使能CAN0和GPIOA的时钟
    rcu_periph_clock_enable(RCU_CAN0);
    rcu_periph_clock_enable(RCU_GPIOA);
    
    //配置GPIO口,CAN0_RX:PA11  CAN0_TX:PA12
    gpio_init(GPIOA,GPIO_MODE_IPU,GPIO_OSPEED_50MHZ,GPIO_PIN_11);
    gpio_init(GPIOA,GPIO_MODE_AF_PP,GPIO_OSPEED_50MHZ,GPIO_PIN_12);
	
	//NVIC中断配置
    nvic_irq_enable(USBD_LP_CAN0_RX0_IRQn ,0,0);
	
	//初始化CAN0参数
    can_struct_para_init(CAN_INIT_STRUCT, &can_parameter);
    can_deinit(CAN0);
    can_parameter.time_triggered = DISABLE;//非时间触发通信模式
    can_parameter.auto_bus_off_recovery = DISABLE;//软件自动离线管理
    can_parameter.auto_wake_up = DISABLE;//睡眠模式通过软件唤醒
    can_parameter.auto_retrans = ENABLE;//报文自动重传
    can_parameter.rec_fifo_overwrite = DISABLE;//报文不锁定,新的覆盖旧的
    can_parameter.trans_fifo_order = DISABLE;
    can_parameter.working_mode = CAN_SILENT_LOOPBACK_MODE;//四种通信模式:正常,回环,静默,回环静默
    can_parameter.resync_jump_width = CAN_BT_SJW_1TQ;//重新同步跳跃宽度
    can_parameter.time_segment_1 = CAN_BT_BS1_5TQ;//时间段 1 占用时间单位
    can_parameter.time_segment_2 = CAN_BT_BS2_4TQ;//时间段 2 占用时间单位
    can_parameter.prescaler = 6;/* 1MBps */
    can_init(CAN0, &can_parameter);

	//初始化CAN过滤器,不过滤任何ID
    can_struct_para_init(CAN_INIT_STRUCT, &can_filter);
    can_filter.filter_number=0;
    can_filter.filter_mode = CAN_FILTERMODE_MASK;
    can_filter.filter_bits = CAN_FILTERBITS_32BIT;
    can_filter.filter_list_high = 0x0000;
    can_filter.filter_list_low = 0x0000;
    can_filter.filter_mask_high = 0x0000;
    can_filter.filter_mask_low = 0x0000;
    can_filter.filter_fifo_number = CAN_FIFO0;
    can_filter.filter_enable = ENABLE;
    can_filter_init(&can_filter);
	
	//使能接收中断,receive FIFO0 not empty interrupt enable
	can_interrupt_enable(CAN0, CAN_INT_RFNE0);
}

/************************************函数功能描述************************************************
Function Name : USBD_LP_CAN0_RX0_IRQHandler(void)
Description   : CAN0的接收中断,如果接收到指定的数据则让can0_receive_flag置1,否则can0_error_flag置1
Input         : 无
Output        : 无
*************************************************************************************************
例如,初始化发送结构体,发送完毕之后就会进入中断
transmit_message.tx_sfid = 0x300>>1;
transmit_message.tx_efid = 0x00;
transmit_message.tx_ft = CAN_FT_DATA;//帧的类型:数据帧或者遥控帧
transmit_message.tx_ff = CAN_FF_STANDARD;//帧的格式:标准帧或者拓展帧
transmit_message.tx_dlen = 2;
transmit_message.tx_data[0] = 0x55;
transmit_message.tx_data[1] = 0xAA;
can_message_transmit(CAN0, &transmit_message);
*************************************************************************************************/
void USBD_LP_CAN0_RX0_IRQHandler(void)
{
    /* check the receive message */
    can_message_receive(CAN0, CAN_FIFO0, &receive_message);
    if((0x300>>1 == receive_message.rx_sfid)&&(CAN_FF_STANDARD == receive_message.rx_ff)&&(2 == receive_message.rx_dlen)){
        can0_receive_flag = SET; 
    }else{
        can0_error_flag = SET; 
    }
}

你可能感兴趣的:(单片机,stm32,嵌入式硬件)