GD32 CAN 2.0 ISO-15765 500K源码

                           前言

硬件说明:
 MCU: GD32C103 120M,128K,32k RAM.
 输入:USB 5V.
 OBD功能口定义:OBD(2,10)VPWM、OBD 7(K线)、OBD 6(CAN H)、OBD 14(CAN L)、OBD 15(L线).
主控电路

软件说明:
一、汽车CAN2.0(双线OBD 6、14)
1、支持波特率:1M、800K、500K、250K、125K、100K、62K、50K、33.3K、25K

二、汽车CAN FD(双线OBD 6、14)
1、仲裁区波特率:1M、500K
2、数据区波特率5M 4M 2M 1M

三、汽车KWP/LIN(OBD 7)总线数据采集说明
1、波特率:5、4800、9600、10416、57600、115200 BPS

三、SAE J1850(OBD 2、10)
1、PWM 协议发送接收
2、VPW 协议发送接收

目录
第2章 CAN 2.0 ISO-15765 500K 2

  1. 电路图 2

  2. 例程说明 2
    (1) 硬件连接 2

  3. 软件设计 2
    (1) main主要流程 2
    (2)can.c主要函数说明 3

  4. PC平台效果 7

    第2章 CAN 2.0 ISO-15765 500K

  5. 电路图
    CAN电路

  6. 例程说明

(1) 硬件连接
用OBD 一分2线接上开发板与CAN 采集器,采集器设置波特率500K不过滤采样。

  1. 软件设计
    CAN1 接单片机 PB8 PB9,500K波特率循环发送 CAN 标准帧扩展帧数据

(1) main主要流程
//初始化IO设置波特率can_configEx(can_500k);
//设置过滤器 CAN_setAllfit();//设置不过滤ID
//发送标准帧 SendISO15765Data(SendData,0xfc00);//15765 STCAN
//发送扩展帧 SendISO15765Data(SendData,0x18DB33F1);//15765 EXCAN

Main() 主要代码
can_configEx(can_500k);//500K 波特率
//CAN1_Config16BitFilter(0xFC00,0xFD00);//设置过滤ID
CAN_setAllfit();//设置不过滤ID

/* main loop */

while (1)
{
SendISO15765Data(SendData,0xfc00);//15765 STCAN
Delay_ms(100);
SendISO15765Data(SendData,0x18DB33F1);//15765 EXCAN
Delay_ms(100);
}
(2)can.c主要函数说明

1 初始化 can_configEx
void can_configEx(uint8_t speed)
{
can_parameter_struct CAN_InitSt;
can_gpio_config();//IO 初始化 PB8 PB9
can_struct_para_init(CAN_INIT_STRUCT, &CAN_InitSt);
/* initialize CAN register */
can_deinit(CAN0);

/* initialize CAN parameters */
CAN_InitSt.time_triggered = DISABLE;
CAN_InitSt.auto_bus_off_recovery = DISABLE;
CAN_InitSt.auto_wake_up = DISABLE;

// 0:使能自动重发 ENABLE
// 1:禁用自动重发
CAN_InitSt.auto_retrans = ENABLE;//报文自动传输 是否开启 如果是发送的环境 最好设置成自动重发

CAN_InitSt.rec_fifo_overwrite = DISABLE;
CAN_InitSt.trans_fifo_order = DISABLE;

CAN_InitSt.working_mode = CAN_NORMAL_MODE;
//CAN_SILENT_MODE静默模式 用于监听总线数据 不发送显性位 当总线有多个节点时 可以选择这个模式
//波特率设置 总线时钟是60M
//BaudRate = APBCLK/BRP*(1+BS1+BS2)
//SamplePoint = ((1+BS1)/(1+BS1+BS2))*100%

CAN_InitSt.resync_jump_width=CANBAUD[speed][0];
CAN_InitSt.time_segment_1=CANBAUD[speed][1];
CAN_InitSt.time_segment_2=CANBAUD[speed][2];
CAN_InitSt.prescaler=CANBAUD[speed][3];//BAUD=60m/((1+6+1)*15)  87.5%
	
	/* initialize CAN */
can_init(CAN0, &CAN_InitSt);

/* configure CAN0 NVIC */
nvic_irq_enable(CAN0_RX0_IRQn, 0, 0);//接收中断 设置
/* enable can receive FIFO0 not empty interrupt */
can_interrupt_enable(CAN0, CAN_INTEN_RFNEIE0);//使能接收中断

}

2 设置过滤器CAN_setAllfit
//不过滤ID
void CAN_setAllfit(void)
{
can_filter_parameter_struct CAN_FilterInitStructure;
can_struct_para_init(CAN_FILTER_STRUCT, &CAN_FilterInitStructure);

	CAN_FilterInitStructure.filter_number = 0;
CAN_FilterInitStructure.filter_mode = CAN_FILTERMODE_MASK;
CAN_FilterInitStructure.filter_bits = CAN_FILTERBITS_32BIT;

CAN_FilterInitStructure.filter_enable = ENABLE;
	 CAN_FilterInitStructure.filter_fifo_number = CAN_FIFO0;
/* configure SFID[10:0] */
CAN_FilterInitStructure.filter_list_high = (uint16_t)0 ;
CAN_FilterInitStructure.filter_list_low = (uint16_t)0;
/* configure SFID[10:0] mask */
CAN_FilterInitStructure.filter_mask_high = (uint16_t)0;
/* both data and remote frames can be received */
CAN_FilterInitStructure.filter_mask_low = (uint16_t)0 ;	
can_filter_init(&CAN_FilterInitStructure);

}
3 设置标准过滤器 CAN1_Config16BitFilter
//标准帧过滤ID 设置
void CAN1_Config16BitFilter(u16 id1, u16 id2)
{
can_filter_parameter_struct CAN_FilterInitStructure;
can_struct_para_init(CAN_FILTER_STRUCT, &CAN_FilterInitStructure);

	CAN_FilterInitStructure.filter_number = 0;//过滤器组
CAN_FilterInitStructure.filter_mode = CAN_FILTERMODE_LIST;//列表模式
CAN_FilterInitStructure.filter_bits = CAN_FILTERBITS_16BIT;//16位ID 模式

CAN_FilterInitStructure.filter_enable = ENABLE;
	 CAN_FilterInitStructure.filter_fifo_number = CAN_FIFO0;
/* configure SFID[10:0] */
CAN_FilterInitStructure.filter_list_high = (uint16_t)id1 ;//ID
CAN_FilterInitStructure.filter_list_low = (uint16_t)id2;//ID
/* configure SFID[10:0] mask */
CAN_FilterInitStructure.filter_mask_high = (uint16_t)id1;//掩码
/* both data and remote frames can be received */
CAN_FilterInitStructure.filter_mask_low = (uint16_t)id2 ;	//掩码
	can_filter_init(&CAN_FilterInitStructure);

}
4 设置扩展过滤器 CAN1_Config32BitFilterExList
//列表模式下 有0~13 共14组 能过滤 28个扩展帧ID
//iBuffer 29 位ID 缓冲区,iSumFiter ID 个数
void CAN1_Config32BitFilterExList(u32 *iBuffer,u8 iSumFiter)
{
u32 id1=0,id2=0;
u8 i=0,iCmt=0,iSum=0;
can_filter_parameter_struct CAN_FilterInitStructure;
iSum=iSumFiter/2;
if(iSumFiter%2)
{
iSum+=1;
}

	for(i=0;i<iSum;i++)
	{
		id1=iBuffer[iCmt++];
		id2=iBuffer[iCmt++];
		
		id1=id1>>3;
		id2=id2>>3;
		
		if(id1==0) id1=0xffffffff;
		if(id2==0) id2=0xffffffff;
		
		can_struct_para_init(CAN_FILTER_STRUCT, &CAN_FilterInitStructure);
		CAN_FilterInitStructure.filter_number = i;
		CAN_FilterInitStructure.filter_mode = CAN_FILTERMODE_LIST;
		CAN_FilterInitStructure.filter_bits = CAN_FILTERBITS_32BIT;
	
		CAN_FilterInitStructure.filter_enable = ENABLE;
		 CAN_FilterInitStructure.filter_fifo_number = CAN_FIFO0;
		/* configure SFID[10:0] */
		CAN_FilterInitStructure.filter_list_high = (uint32_t)(id1>>13);
		CAN_FilterInitStructure.filter_list_low = (uint32_t)((id1<<3)|4);
		/* configure SFID[10:0] mask */
		CAN_FilterInitStructure.filter_mask_high = (uint32_t)(id2>>13);
		/* both data and remote frames can be received */
		CAN_FilterInitStructure.filter_mask_low = (uint32_t)((id2<<3)|4);
		can_filter_init(&CAN_FilterInitStructure);
	}

}

5 CAN2.0 发送命令 SendISO15765Data
//iCanId CAN ID ,已经移位的 FC00(7E0)
// 15765 标准帧
//cmdaddr[0]= 发送长度
//cmdaddr[1…] 发送的数据
//注: iCanId>0xFFFF 时为扩展帧
// 返回1 成功 返回 0 失败
u8 SendISO15765Data(u8 *cmdaddr,u32 iCanId) //
{
u32 i=0,tmp=0;
uint8_t TransmitMailbox=0;
u8 Stollen=cmdaddr[0]&0x0F;
if(Stollen==0) return 1;

if(Stollen>8)  Stollen=8;
//初始化参数
can_trasnmit_message_struct   TbufMege;
can_struct_para_init(CAN_TX_MESSAGE_STRUCT, &TbufMege);	
if(iCanId>0Xffff)//扩展帧
{
	TbufMege.tx_sfid = 0;
	TbufMege.tx_efid = iCanId/0X08;
	TbufMege.tx_ff = CAN_FF_EXTENDED;
}
else
{
	TbufMege.tx_sfid = iCanId/0X20;
	TbufMege.tx_efid = 0x00;
	TbufMege.tx_ff = CAN_FF_STANDARD;
}
TbufMege.tx_ft = CAN_FT_DATA;  

TbufMege.tx_dlen = Stollen;
for(u8 Sidx = 0; Sidx < Stollen; Sidx ++)
{
TbufMege.tx_data[Sidx] = cmdaddr[Sidx+1];
}
can_transmit_state_enum iFlag;
TransmitMailbox=can_message_transmit(CAN0, &TbufMege);
// //判断是否发送成功
GetTimer6Cnt();//清空
i=0;
while(1)
{
i++;
iFlag=can_transmit_states(CAN0,TransmitMailbox);
if(iFlag==CAN_TRANSMIT_OK) break;//校验是否发送成功
if(i>0xFFFFFF) break;

	 tmp=GetTimer6CntEx();
	 if(tmp>1000*500) break;
 }

return 1;
}

  1. PC平台效果
    EcuSimulator 工具设置CAN2.0 500K不过滤,显示数据如下图所示
    上位机

单片机源码地址
https://github.com/siyuan1644/GD32_CAN-2.0-ISO-15765.git

硬件地址
硬件地址

  • 0
    点赞
  • 10
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值