--for Windows 95/98/2000
Pcicandrv.LIB - CAN总线函数库(适用于Windows 95/98/2000):
1.自定义数据结构说明
1.1 PORT_STRUCT 结构定义
PORT_STRUCT 结构:定义读取的PCI板卡 typedef struct _tagPORT_STRUCT {
BYTE card; // index of card(start from 0) BYTE value; // for some particular use } PORT_STRUCT; 成员变量说明:
card: 表示读取哪一个PCI非智能卡,基值必须从0开始;
value: 为将来功能的扩展预留;
1.2 PORT_CONFIG 结构定义
PORT_CONFIG 结构: 配置PCI非智能卡的工作方式、ID和波特率 typedef struct _tag PORT_CONFIG {
WORD workMode; // 0 for 11-bit;
// 1 for 29-bit WORD filterMode; // 0 for single filter mode, // 1 for dual filter mode;
DWORD accCode; // accept code DWORD accMask; // accept mask
BYTE timer0; // timer0 register (set baudrate) BYTE timer1; // timer1 register BYTE control; // enable interrupt }PORT_CONFIG; 成员变量说明:
workMode : 0 - 使用 11位 CAN_ID;
1- 使用 29位 CAN_ID; filterMode: 0 -CAN控制器采用单滤波方式; 1 -CAN控制器采用双滤波方式;
accCode: 设定的CAN控制器节点ID;
accMask: 设定的与CAN_ID对应的屏蔽码 ; timer0: 设定的CAN控制器 time0寄存器内容(用
于设定波特率);
timer1: 设定的CAN控制器 time1寄存器内容(用于设定波特率);
control: 用于设定允许开放的中断 0-禁止中断 1-开放中断
control.7 control.0
BEIE ALIE EPIE WUIE DOIE EIE TIE RIE BEIE: bus error interrupt enable
ALIE : arbitration lost interrupt enable EPIE: error passive interrupt enable WUIE: wake-up interrupt enable
DOID: data overrun interrupt enable EIE: error warning interrupt enable TIE: transmit interrupt enable RIE: receive interrupt enable
波特率与Time0、Time1寄存器设定对照表
Timer0 3fh 1fh 0fh 07h 07h 03h 03h 03h 01h 01h 00h 00h 00h 00h Timer1 Ffh Ffh Ffh Ffh 2fh Ffh 2fh 1ch Ffh 1ch Ffh 1ch 16h 14h Baudrate(bps) 5k 10k 20k 40k 50K 80k 100k 125k 160k 250k 320k 500k 800k 1000k 1.3 PORT_REG 结构定义
PORT_REG 结构: 用于读/写CAN控制器内的寄存器的数据结构。 typedef struct _tagPORT_REG {
BYTE card; // index of card(start from 0)
BYTE reg; // one of register in SJA1000
BYTE value; // for Reading: value read from one register // for writting: value want to write to one register }PORT_REG;
成员变量说明:
card: 表示读取哪一个PCI非智能卡,基值必须从0开始; reg: 设定读取的CAN控制器的寄存器; value: 读/写的寄存器内容
读操作:保存从寄存器读取的数据 写操作:保存写到寄存器的数据
1.4 CAN_PACKET 结构定义
PORT_ PACKET 结构: CAN数据帧结构,用于发送和接收函数。 typedef struct _tagCAN_PACKET {
DWORD CAN_ID; // CAN ID field (32-bit unsigned integer) BYTE rtr; // CAN RTR bit.
BYTE length; // Length of data field. BYTE data[8]; // Data (8 bytes maximum) DWORD time; // Reserved for future use BYTE reserved; // Reserved byte } CAN_PACKET; 成员变量说明:
CAN_ID; CAN_ID(无符号32位数) rtr: CAN RTR 位 0-数据帧 1-远程帧
length: 数据长度(以字节为单位,最多8个字节) data[8]: 数据(最多8个字节); time: 为将来功能扩展预留; reserved: 为将来功能扩展预留;
1.5 CAN_PACKET1000 结构定义
PORT_ PACKET1000 结构: 定义此数据结构用于一次性全部读取数据缓冲区内容;
typedef struct _tagCAN_PACKET1000 {
WORD num;
CAN_PACKET packet[1000]; } CAN_PACKET1000; 成员变量说明:
num: 实际从数据缓冲区内读取的CAN数据帧数量(0~1000)
packet[1000]:保存从数据缓冲区内读取的CAN数据帧内
容
2. 函数使用说明
2.1打开PCI非智能卡函数 int CAN_Open(void) 参数: 无
返回值: 1 - 成功
0 - 失败
2.2初始化函数
int CAN_Init(PORT_STRUCT *ptrStruct,PORT_CONFIG *ptrConfig) 参数: ptrStruct - 结构PORT_STRUCT的指针
ptrConfig - 结构PORT_CONFIG的指针 返回值: 1 - 打开PCI卡成功
0 - 打开PCI卡失败 -1 - 设定的PCI板卡不存在
说明:ptrStruct结构中的card用以选择操作的PCI板卡,ptrConfig中的参数用以
设定CAN控制器的工作方式、滤波方式、波特率以及控制器开放的中断。
CAN控制器的波特率的设定以16MHZ晶振为标准。如果使用内存缓冲区模式
(使用计算机内存,最多可存储1000帧数据),请开放CAN控制器的接收
中断允许。
注意:以下对各函数中的ptrStruct结构不再加以说明,如非特别声明,均 用于选择操作的PCI板卡。
2.3 波特率自动设定函数
int CAN_Detect_Baudrate(PORT_STRUCT *ptrStruct) 参数: ptrStruct - 结构PORT_STRUCT的指针 返回值: 1 - 自动设定波特率成功
0 - 自动设定波特率失败 -1 - 设定的PCI板卡不存在
说明: 自动测试的波特率只能从给定的波特率列表中选择,而且只能工作于
网络上多个CAN节点(>2)同时工作的情况。
2.4 禁止数据接收函数
int CAN_Disable_Receive(PORT_STRUCT *ptrStruct) 参数: ptrStruct - 结构PORT_STRUCT的指针 返回值: 1 - 禁止数据接收成功
0 - 禁止数据接收失败
-1 - 设定的PCI板卡不存在
说明: 禁止接收函数可以使CAN控制器不再接收其它节点发送的数据,但依
然能够正常发送数据。
2.5 开放数据接收函数
int CAN_Enable_Receive(PORT_STRUCT *ptrStruct) 参数: ptrStruct - 结构PORT_STRUCT的指针 返回值: 1 - 开放数据接收成功
0 - 开放数据接收失败 -1 - 设定的PCI板卡不存在
说明: 使已禁止接收数据的CAN控制器恢复接收数据功能。 2.6 读取错误警告函数(Error Warning Limit)
int CAN_Get_ErrorWarningLimit(PORT_STRUCT *ptrStruct) 参数: ptrStruct - 结构PORT_STRUCT的指针 返回值: 1 - 读取错误警告成功
0 - 读取错误警告失败 -1 - 设定的PCI板卡不存在
说明:CAN控制器复位后默认的错误警告数为96。
注意:读取的错误警告数从ptrStruct结构的value变量获得。 2.7 设置错误警告函数(Error Warning Limit)
int CAN_Set_ErrorWarningLimit(PORT_STRUCT *ptrStruct) 参数: ptrStruct - 结构PORT_STRUCT的指针 返回值: 1 - 设置错误警告成功
0 - 设置错误警告失败 -1 - 设定的PCI板卡不存在
说明:重新设置的错误警告值(<255)请赋于ptrStruct结构的value变
量后调用此函数。
2.8 读取发送错误计数器函数
int CAN_Get_TxErrorCount(PORT_STRUCT *ptrStruct) 参数: ptrStruct - 结构PORT_STRUCT的指针 返回值: 1 - 读取发送错误计数成功
0 - 读取发送错误计数失败 -1 - 设定的PCI板卡不存在
说明:CAN控制器复位后默认的发送错误计数器数值为0。
注意:读取的发送错误计数从ptrStruct结构的value变量获得。
2.9 设置发送错误计数器函数
int CAN_Set_TxErrorCount(PORT_STRUCT *ptrStruct) 参数: ptrStruct - 结构PORT_STRUCT的指针
返回值: 1 - 设置发送错误计数成功
0 - 设置发送错误计数失败 -1 - 设定的PCI板卡不存在
说明:重新设置的发送错误计数(<255)请赋于ptrStruct结构的value变量
后调用此函数。
2.10 读取接收错误计数器函数
int CAN_Get_RxErrorCount(PORT_STRUCT *ptrStruct) 参数: ptrStruct - 结构PORT_STRUCT的指针 返回值: 1 - 读取接收错误计数成功
0 - 读取接收错误计数失败 -1 - 设定的PCI板卡不存在
说明:CAN控制器复位后默认的接收错误计数器数值为0。
注意:读取的接收错误计数从ptrStruct结构的value变量获得。
2.11 读取总线错误代码函数
int CAN_Get_ErrorCode(PORT_STRUCT *ptrStruct) 参数: ptrStruct - 结构PORT_STRUCT的指针 返回值: 1 - 读取总线错误代码成功
0 - 读取总线错误代码失败 -1 - 设定的PCI板卡不存在
说明:读取的总线错误代码从ptrStruct结构的value变量获得。
2.12 查询是否有接收数据函数
int CAN_Inquiry_Rece(PORT_STRUCT *ptrStruct)
参数: ptrStruct - 结构PORT_STRUCT的指针 返回值: 1 - 有接收数据
0 - 无接收数据
-1 - 设定的PCI板卡不存在 说明:此函数从CAN控制器缓冲区或内存缓冲区内判断是否有已接收的数
据。
2.13 读取接收缓冲区内数据帧数量函数
int CAN_Get_RxBufferCount(PORT_STRUCT *ptrStruct) 参数: ptrStruct - 结构PORT_STRUCT的指针 返回值: >= 0 - 接收缓冲区内数据帧的数量 -1 - 设定的PCI板卡不存在 说明:此函数从CAN控制器缓冲区或内存缓冲区内读取已接收的数据帧数
量。
2.14 清除接收缓冲区内数据函数
int CAN_Clear_RxBuffer(PORT_STRUCT *ptrStruct) 参数: ptrStruct - 结构PORT_STRUCT的指针 返回值: 1 - 清除接收缓冲区内数据成功
0 - 清除接收缓冲区内数据失败 -1 - 设定的PCI板卡不存在 说明:此函数清除CAN控制器缓冲区或内存缓冲区内已接收的数据帧。
2.15接收数据帧函数(一次只读取一帧数据)
int CAN_Rece(PORT_STRUCT *ptrStruct,CAN_PACKET *ptrPacket) 参数: ptrStruct - 结构PORT_STRUCT的指针
ptrPacket - 结构CAN_PACKET的指针 返回值: 1 - 接收数据成功
0 - 无接收数据
-1 - 设定的PCI板卡不存在 说明:此函数从CAN控制器缓冲区或内存缓冲区内读取已接收的数据帧。
接收的数据从ptrPacket的成员变量Data中读取。详细数据结构请参看
自定义的CAN_PACKET结构。
注意:以下各函数中的ptrPacket结构均指CAN数据帧结构,不再加以说 明。
2.16读缓冲区数据帧函数(一次读取全部帧数据) int CAN_Read_RxBuffer(PORT_STRUCT
*ptrStruct,CAN_PACKET1000 *ptrPacket1000)参数: ptrStruct - 结构PORT_STRUCT的指针
ptrPacket1000 - 结构CAN_PACKET1000的指针 返回值: 1 - 接收数据成功
0 - 无接收数据
-1 - 设定的PCI板卡不存在 说明:此函数从CAN控制器缓冲区或内存缓冲区内一次性全部读取已接收的
数据帧。接收的数据帧从ptrPacket1000的成员变量ptrPacket1000中
读取, 实际接收到的数据帧数量从ptrPacket1000的成员变量num中
读取。详细的数据结构请参看自定义的CAN_PACKET1000结构。
2.17 查询是否可以发送数据函数
int CAN_Inquiry_Trans(PORT_STRUCT *ptrStruct) 参数: ptrStruct - 结构PORT_STRUCT的指针
返回值: 1 - CAN控制器空闲,可以发送数据
0 - CAN控制器正在发送数据…
-1 - 设定的PCI板卡不存在
说明:此函数判断CAN控制器状态,判断是否可以发送新的数据帧。
2.18 清除正在发送的数据函数
int CAN_Clear_TxBuffer(PORT_STRUCT *ptrStruct) 参数: ptrStruct - 结构PORT_STRUCT的指针 返回值: 1 - 清除正在发送的数据成功
0 - 清除正在发送的数据失败 -1 - 设定的PCI板卡不存在 说明:如果CAN控制器内有正在发送的数据帧,则使此数据帧夭折发送。
2.19发送数据帧函数
int CAN-Trans (PORT_STRUCT *ptrStruct,CAN_PACKET *ptrPacket) 参数: ptrStruct - 结构PORT_STRUCT的指针
ptrPacket - 结构CAN_PACKET的指针 返回值: 1 - 数据帧成功写入发送缓冲区等待发送 0 - CAN控制器无法发送数据帧 -1 - 设定的PCI板卡不存在
说明: 此函数将要发送的数据帧写入发送缓冲区等待发送,但无法保证数据
帧一定发送成功;如果用户需要判断,可以调用CAN_Inquiry_Trans
()函数判断是否已经发送成功。 2.20 查询CAN控制器状态函数
int CAN_Inquiry_Status(PORT_STRUCT *ptrStruct) 参数: ptrStruct - 结构PORT_STRUCT的指针
返回值: 16 Bit 值 高位字节:CAN中断寄存器内容 低位字节:CAN状态寄存器内容
说明:此函数读取CAN中断寄存器和CAN状态寄存器内容 2.21 清除数据过载函数
int CAN_Clear_Overrun (PORT_STRUCT *ptrStruct) 参数: ptrStruct - 结构PORT_STRUCT的指针 返回值: 1 - 清除数据过载成功
0 - 清除数据过载失败 -1 - 设定的PCI板卡不存在
2.22 CAN控制器软件复位函数
int CAN_Soft_Reset(PORT_STRUCT *ptrStruct)
参数: ptrStruct - 结构PORT_STRUCT的指针 返回值: 1 - 软件复位成功
0 - 软件复位失败
-1 - 设定的PCI板卡不存在 说明:软件复位强制CAN控制器进入复位模式,待初始化后重新开始工作;此
函数只适用于CAN控制器积累的错误尚不足以使控制器脱离总线状态
时。
2.23 CAN控制器硬件复位函数
int CAN_Hard_Reset(PORT_STRUCT *ptrStruct)
参数: ptrStruct - 结构PORT_STRUCT的指针 返回值: 1 - 硬件复位成功
0 - 硬件复位失败
-1 - 设定的PCI板卡不存在
说明: 硬件复位强制在CAN控制器的Reset Pin加入复位脉冲,以使CAN控制
器重新上电。此函数适用于CAN控制器脱离总线状态时。
2.24 读CAN控制器的寄存器函数
int CAN_Read_Register(PORT_REG *ptrPortReg) 参数: ptrPortReg - 结构PORT_REG的指针 返回值: 1 - 读寄存器成功
0 - 读寄存器失败
-1 - 设定的PCI板卡不存在
说明: ptrPortReg的成员变量card用以选择CAN控制器;reg用以选择CAN
控制器内的寄存器;value用以保存读取的寄存器内容。
2.25 写CAN控制器的寄存器函数
int CAN_Write_Register(PORT_REG *ptrPortReg) 参数: ptrPortReg - 结构PORT_REG的指针 返回值: 1 - 写寄存器成功
0 - 写读寄存器失败 -1 - 设定的PCI板卡不存在
说明: ptrPortReg的成员变量card用以选择CAN控制器;reg用以选择CAN
控制器内的寄存器; value 用以保存写入寄存器的内容。
2.26 关闭PCI非智能卡函数 int CAN_Close(void) 参数: 无
返回值: 1 - 成功
0 - 失败
3. CAN帧标准数据格式
3.1 CAN2.0B 标准帧数据格式(11 Bit CAN ID)
CAN标准帧信息包括分为两部分:信息和数据部分。前3个字节为信息部分。第1个
字节是帧信息,FF为帧格式;RTR位为远程发送请求,0 - 发送数据帧,1 - 发送远程帧;X位为无关位;最后4位DLC是数据长度,即所发数据的实际长度,单位:字节。第2、3个字节的前11位为CAN_ID标识符(2个字节),包含本信息包的目的站地址。其余八个字节是数据部分,存有实际发送的数据。详见下表:
字节1 字节2 字节3 字节4 字节5 字节6 字节7 字节8 字节9 字节10 字节11 7 FF 6 RTR 5 X 4 X 3 2 1 0 DLC(数据长度) (地址标识符) ID.28-ID.21 ID.20-ID.18 X X X X X 数 据 1 数 据 2 数 据 3 数 据 4 数 据 5 数 据 6 数 据 7 数 据 8 3.2 CAN2.0B 扩展帧数据格式(29 Bit CAN ID)
CAN扩展帧信息包括分为两部分,信息和数据部分。前5个字节为信息部分。第1个
字节是帧信息,FF为帧格式;RTR位为远程发送请求,发送数据帧时为0,发送远程帧时为1;X位为无关位;最后4位DLC是数据长度,即所发数据的实际长度,单位:字节。第2、3、4、5字节的前29位为标识符(4个字节),包含本信息包的目的站地址。其余八个字节是数据部分,存有实际要发的数据。详见下表:
7 6 5 4 3 2 1 0 字节1 字节2 字节3 字节4 字节5 字节6 字节7 字节8 字节9 字节10 字节11 字节12 字节13 FF RTR X X DLC(数据长度) (地址标识符) ID.28-ID.21 ID.20-ID.13 ID.12-ID.5 ID.4-ID.0 数 据 1 数 据 2 数 据 3 数 据 4 数 据 5 数 据 6 数 据 7 数 据 8 X X X 注意:在我们定义函数中提供的自定义数据格式,发送/接收时自动转化 为以上标准的CAN帧数据格式,用户无须转换。
3.3 CAN_ID(接收码)与屏蔽码的设定
CAN控制器通过设定屏蔽码可以实现有选择的接收报文(0-Mask,1-UnMask)。我
们定义的函数可以支持CAN控制器分别工作于single filter mode 和dual filtermode 方式,因此接收码与屏蔽码相应的设置方式也不相同。 例如:
对于11bit CAN_ID(标准帧):
设置接收码为 0x2, 则 ptrConfig->accCode = 0x0002; 假定只接收发往CAN节点0、1、2的报文,则设置屏蔽码如下: single filter 模式:
无法实现只接收发往CAN节点0、1、2的报文,但设置
ptrConfig->accMask = 0x0003;
可以接收发往CAN节点0、1、2、3的报文。 dual filter 模式:
可以实现只接收发往CAN节点0、1、2的报文,设置
ptrConfig->accMask = 0x00010000;
设置的前一个filter 0x0001 只接收发往节点0、
1的报文;设置的后一
个filter 0x0000只接收发往节点2的报文; 对于29 bit CAN_ID(扩展帧):
设置接收码为 0x2, 则 ptrConfig->accCode = 0x00000002; 假定只接收发往CAN节点0、1、2的报文,则设置屏蔽码如下: single filter 模式:
无法实现只接收发往CAN节点0、1、2的报文,但设置
ptrConfig->accMask = 0x00000003; 可以接收发往CAN节点0、1、2、3的报文。 dual filter 模式:
对于扩展帧的双滤波方式,每个滤波器仅屏蔽接收报文CAN_ID的
ID.28~ID.13,无法实现对ID.12~ID.0的屏蔽,因此无法实现只接收发
往CAN节点0、1、2的报文。
关于CAN控制器接收码、屏蔽码以及滤波器的工作方式的详细细节,请参见SJA1000的使用说明书。 3.4 特别说明
针对瑞隆德公司生产的PCI非智能CAN通信卡,我们开发了兼容
CAN2.0A协议和AN2.0B协议的自定义函数,但由于在以前开发的基于ISA的非智能通信卡的CAN2.0A协议实际只使用了8 bit 作为CAN_ID,因此如果使用北京瑞隆德公司生产的基于ISA的非智能卡CAN2.0A协议和基于PCI的非智能卡通信时,对CAN节点ID的解析会发生歧义。
下图表示了通信过程中对CAN_ID解析的不同之处。
从上图可以看到,ISA卡的ID.2~ID.0未用,而PCI卡使用了ID.2~ID.0,因此接收后需要转换。
例如: ISA卡 发送报文给CAN_ID 0x03,ID.10~ID.3 = 00000011B = 0x03,而在PCI卡上接收到的CAN_ID报文为ID.10~ID.0 = 00000011000B = 0x018, 因此在PCI卡上接收的CAN_ID应该右移3位才能得到ISA上发送的正确的ID号,反之亦然。
以上的通信过程丝毫不会影响数据在CAN总线上的传输,仅仅因为CAN_ID使用的不同需要加以解析。
因篇幅问题不能全部显示,请点此查看更多更全内容
Copyright © 2019- oldu.cn 版权所有 浙ICP备2024123271号-1
违法及侵权请联系:TEL:199 1889 7713 E-MAIL:2724546146@qq.com
本站由北京市万商天勤律师事务所王兴未律师提供法律服务