基于CCP协议的CAN总线
来源:互联网 发布:anker 充电宝 知乎 编辑:程序博客网 时间:2024/06/03 01:42
作者:owen_09
转自:http://blog.csdn.net/owen_09/article/details/38336271
CCP通信协议:主从式,主设备通过CAN总线与多台从设备相连,主设备室测量标定系统 ,从设备是需要标定的ECU,主设备首先与其中一个从设备建立逻辑连接,主、从设备之间的所有的数据传递均由主机控制,从设备执行主设备命令后返回包含命令响应值或错误代码等信息的报文,同时从设备可以根据主设备通过控制命令设置的列表信息来定时地向主设备传送变量信息,数据的传递是由主设备初始化并且从设备来执行的,并且是由固定的循环采样频率或者事件触发的。
主设备通过USB-CAN接口与从设备连接,符合CAN2.0协议。
通信过程中,所有报文均为8个字节,包括命令、数据、数据长度、地址等信息
该通信协议参照CCP协议,可以与INCA等标定软件接口。
CAN通信:采用两个报文数据对象 CRO和DTO (命令接收对象)(命令发送对象)每个对象根据其数据流向,都有一个唯一的ID标示符进行标示,ID标识符可以由用户自己设定。
命令接收对象(CRO):
用于传递指令代码和内部功能码或主、从设备之间交换的存储区数据
表1
CMD (1 Byte):
命令代码。
CTR (1 Byte):
命令计数器。
Parameter and Data(6 Byte):
参数和数据场,命令相关的数据或参数
数据接收对象(DTO):
数据传输对象(DTO)指由从设备反馈的报文。DTO根据报文首字节PID的值可以由三种形式,见表2:
PID值
数据传输类型
备注
0xFF
CRM(Command Return Message)
由从设备发送,反馈CRO命令的报文
0xFE
Event Message
当从设备检测到内部发生错误机制时,由从设备自行向主设备发送,报告其当前的运行状态,并请求主设备暂停当前工作进程以处理发生的错误
0-0xFD
DAQ-DTO(Data Acquisition-DTO)
用于DAQ模式,由从设备定期向主设备发送。
根据对象描述表(ODT),确定需要上传的变量
CRM-Event Message报文帧格式
表3:场说明
PID(1 Byte)
其值代表了DTO的类型
ERR(1 Byte)
命令返回错误代码
CTR(1 Byte)
命令计数器,与接收的相等。
Parameter and Data Field
参数和数据场,命令相关的数据或参数
(2). DAQ-DTO(Data Acquisition-DTO)的报文帧:
3. 协议命令列表及说明(标注绿色字体部分逐步补充完整)
3.1 命令列表:
命令名称
代码
说明
CONNECT
0x01
创建一个ECU的连接
SET_MTA
0x02
设置MTA地址
DNLOAD
0x03
下载最多5个字节数据到ECU
DNLOAD_6
0x23
下载6个字节数据到ECU
UPLOAD
0x04
从ECU上载最多5个字节数据
SHORT_UP
0x0F
从ECU上载最多5个数据(不用MTA)
DISCONNECT
0x07
断开到该ECU的连接
GET_DAQ_SIZE
0x14
得到指定DAQ列表大小
SET_DAQ_PTR
0x15
选中某指定DAQ列表中某ODT的某元素
WRITE_DAQ
0x16
设定该元素指定的地址
START_STOP
0x06
开始/停止采集指定的DAQ列表
EXCHANGE_ID
0x17
得到该ECU的标识符
GET_SEED
0x12
得到计算密钥的种子(SEED)
UNLOCK
0x13
要求ECU释放某种功能
SET_S_STATUS
0x0C
设置当前会话状态
GET_S_STATUS
0x0D
得到当前会话状态
BUILD_CHKSUM
0x0E
计算指定区域的校验和
CLEAR_MEMORY
0x10
清除某内存区域
PROGRAM
0x18
FLASH编程(最多5个字节)
PROGRAM_6
0x22
FLASH编程(6个字节)
MOVE
0x19
从MTA0处拷贝指定长度的字节到MTA1处
TEST
0x05
测试当前在线的从设备
GET_ACTIVE_CAL_PAGE
0x09
得到当前标定页(RAM or FLASH)
DIAG_SERVICE
0x20
ACTION_SERVICE
0x21
3.2命令返回错误代码
代码
描述
种类
状态改变
0x00
正确接收,无错误
0x01
DAQ处理器过载
0x10
命令处理器忙
0x11
DAQ处理器忙
。。。
待续
3.3命令详细说明
3.3.1CONNECT命令:
命令接收对象(CRO):
位(bit)
数据类型
描述
0
字节
命令代码(0x01)
1
字节
命令计数器
2
字
站地址
4-7
字节
填0(不关心)
数据传送对象(DTO):
位(bit)
数据类型
描述
0
字节
命令代码(0xFF)
1
字节
命令返回代码
2
字节
命令计数器
3-7
字节
填0(不关心)
程序:connect命令
UINT8 Connect(UINT16 wStationAddr) {
UINT8pbCROData[8];
pbCROData[0] = CC_CONNECT;
pbCROData[1] = m_bCTR ++;
// intel format
pbCROData[2] = (UINT8)(wStationAddr &0xFF);
pbCROData[3] = (UINT8)(wStationAddr >> 8);
// don't care
pbCROData[4] = 0x00;
pbCROData[5] = 0x00;
pbCROData[6] = 0x00;
pbCROData[7] = 0x00;
UINT8bRlt;
UINT8pbDTOData[8];
if (CRC_OK != (bRlt = SendPackage(pbCROData,pbDTOData, TRANSMIT_TIMEOUT))) {
return bRlt;
}
// Response
// 0 Packet ID: 0xFF
// 1 Command Return Code
// 2 Command Counter = CTR
// 3..7 don't care
if (CRC_OK == pbDTOData[1]) {
m_bConnected = TRUE;
}
return pbDTOData[1];
}
3.3.2SET_MTA命令:
命令接收对象(CRO):
位(bit)
数据类型
描述
0
字节
命令代码(0x02)
1
字节
命令计数器
2
字节
存贮器传输地址(MTA0,MTA1)
3
字节
地址扩展
4-7
无符号长整形
地址
数据传送对象(DTO):
0
字节
命令代码(0x01)
1
字节
命令计数器
2
字
站地址
4-7
字节
填0(不关心)
数据传送对象(DTO):
位(bit)
数据类型
描述
0
字节
命令代码(0xFF)
1
字节
命令返回代码
2
字节
命令计数器
3-7
字节
填0(不关心)
3.3.2SET_MTA命令:
命令接收对象(CRO):
位(bit)
数据类型
描述
0
字节
命令代码(0x02)
1
字节
命令计数器
2
字节
存贮器传输地址(MTA0,MTA1)
3
字节
地址扩展
4-7
无符号长整形
地址
数据传送对象(DTO):
位(bit)
数据类型
描述
0
字节
命令代码(0xFF)
1
字节
命令返回代码
2
字节
命令计数器
3-7
字节
填0(不关心)
UINT8SetMTA(UINT8 bMTANumber, UINT8 bAddrExt, UINT32 dwAddr) {
UINT8pbCROData[8];
pbCROData[0]= CC_SET_MTA;
pbCROData[1] = m_bCTR ++;
pbCROData[2] = bMTANumber;
pbCROData[3] = bAddrExt;
pbCROData[4] = (UINT8)(dwAddr >> 24);
pbCROData[5] = (UINT8)(dwAddr >> 16);
pbCROData[6] = (UINT8)(dwAddr >> 8);
pbCROData[7] = (UINT8)(dwAddr >> 0);
UINT8bRlt;
UINT8pbDTOData[8];
// if (CRC_OK != (bRlt = SendMessage(pbCROData, pbDTOData,TRANSMIT_TIMEOUT))) {
if (CRC_OK != (bRlt = SendPackage(pbCROData,pbDTOData, 2000))) {
return bRlt;
}
// Response
// 0 Packet ID: 0xFF
// 1 Command Return Code
// 2 Command Counter = CTR
// 3..7 don't care
return pbDTOData[1];
}
3.3.3 DNLOAD命令:
命令接收对象(CRO):
位(bit)
数据类型
描述
0
字节
命令代码(0x03)
1
字节
命令计数器
2
字节
需下传的数据长度
3-7
字节
数据
数据传送对象(DTO):
位(bit)
数据类型
描述
0
字节
命令代码(0xFF)
1
字节
命令返回代码
2
字节
命令计数器
3
字节
MTA0扩展位
4-7
字节
执行后MTA0地址(即地址加上长度)
UINT8Download(UINT8 &bSize, PUINT8 pbData, UINT8 &bExtAddr, UINT32&dwAddr) {
UINT8pbCROData[8];
UINT8i;
pbCROData[0] = CC_DNLOAD;
pbCROData[1] = m_bCTR ++;
pbCROData[2] = bSize;
if ((NULL == pbData)) {
return CRC_CMD_SYNTAX;
}
if (bSize > 5) {
bSize = 5;
}
for (i = 0; i < bSize; i ++) {
pbCROData[3 + i] = pbData[i];
}
for (; i < 5; i ++) {
pbCROData[3 + i] = 0x00;
}
UINT8bRlt;
UINT8pbDTOData[8];
if (CRC_OK != (bRlt = SendPackage(pbCROData,pbDTOData, TRANSMIT_TIMEOUT))) {
return bRlt;
}
// Response
// 0 Packet ID: 0xFF
// 1 Command Return Code
// 2 Command Counter = CTR
// 3 MTA0 extension (after post-increment)
// 4..7 MTA0 address (after post-increment)
bExtAddr = pbDTOData[3];
dwAddr= (((UINT32)pbDTOData[4]) << 24) ||
(((UINT32)pbDTOData[5]) << 16) ||
(((UINT32)pbDTOData[6]) << 8) ||
(((UINT32)pbDTOData[7]) << 0);
return pbDTOData[1];
}
3.3.4UPLOAD命令:
命令接收对象(CRO):
位(bit)
数据类型
描述
0
字节
命令代码(0x04)
1
字节
命令计数器
2
字节
需上传的数据长度
3-7
字节
填0
数据传送对象(DTO):
位(bit)
数据类型
描述
0
字节
命令代码(0xFF)
1
字节
命令返回代码
2
字节
命令计数器
3-7
字节
上传的数据
UINT8 Upload(UINT8 &bSize, PUINT8 pbData) {
UINT8pbCROData[8];
UINT8i;
if ((NULL == pbData)) {
return CRC_CMD_SYNTAX;
}
if (bSize > 5) {
bSize = 5;
}
pbCROData[0]= CC_UPLOAD;
pbCROData[1] = m_bCTR ++;
pbCROData[2] = bSize;
// don't care
pbCROData[3] = 0x00;
pbCROData[4] = 0x00;
pbCROData[5] = 0x00;
pbCROData[6] = 0x00;
pbCROData[7] = 0x00;
UINT8bRlt;
UINT8pbDTOData[8];
if (CRC_OK != (bRlt = SendPackage(pbCROData,pbDTOData, TRANSMIT_TIMEOUT))) {
return bRlt;
}
// Response
// 0 Packet ID: 0xFF
// 1 Command Return Code
// 2 Command Counter = CTR
// 3..7 requested data bytes
for (i = 0; i < bSize; i ++) {
pbData[i] = pbDTOData[3 + i];
}
return pbDTOData[1];
}
3.3.5 SHORT UPLOAD命令:
命令接收对象(CRO):
位(bit)
数据类型
描述
0
字节
命令代码(0x0F)
1
字节
命令计数器
2
字节
需上传的数据长度
3
字节
地址扩展
4-7
字节
地址
数据传送对象(DTO):
位(bit)
数据类型
描述
0
字节
命令代码(0xFF)
1
字节
命令返回代码
2
字节
命令计数器
3-7
字节
上传的数据
3.3.6DISCONNECT命令:
命令接收对象(CRO):
位(bit)
数据类型
描述
0
字节
命令代码(0x07)
1
字节
命令计数器
2
字节
0x00 暂时断开, 0x01 断开
3
字节
不关心
4-5
字节
站地址(低位在前)
6-7
字节
填0(不关心)
数据传送对象(DTO):
位(bit)
数据类型
描述
0
字节
命令代码(0xFF)
1
字节
命令返回代码
2
字节
命令计数器
3-7
字节
填0(不关心)
UINT8 ShortUpload(UINT8 bSize, UINT8 bAddrExt, UINT32dwAddr, PUINT8 pbData) {
UINT8pbCROData[8];
UINT8i;
if ((NULL == pbData)) {
return CRC_CMD_SYNTAX;
}
if (bSize > 5) {
bSize = 5;
}
pbCROData[0] = CC_SHORT_UPLOAD;
pbCROData[1] = m_bCTR ++;
pbCROData[2] = bSize;
pbCROData[3] = bAddrExt;
pbCROData[4] = (UINT8)(dwAddr >> 24);
pbCROData[5] = (UINT8)(dwAddr >> 16);
pbCROData[6] = (UINT8)(dwAddr >> 8);
pbCROData[7] = (UINT8)(dwAddr >> 0);
UINT8bRlt;
UINT8pbDTOData[8];
if(CRC_OK != (bRlt = SendPackage(pbCROData, pbDTOData, TRANSMIT_TIMEOUT))) {
return bRlt;
}
// Response
// 0 Packet ID: 0xFF
// 1 Command Return Code
// 2 Command Counter = CTR
// 3..7 requested data bytes
for (i = 0; i < bSize; i ++) {
pbData[i] = pbDTOData[3 + i];
}
return pbDTOData[1];
}
3.3.7GET_DAQ_SIZE命令:
命令接收对象(CRO):
位(bit)
数据类型
描述
0
字节
命令代码(0x14)
1
字节
命令计数器
2
字节
DAQ表号(0,1…)
3
字节
填0(不关心)
4-7
字节
CAN 识别号(可选,暂不使用)
数据传送对象(DTO):
位(bit)
数据类型
描述
0
字节
命令代码(0xFF)
1
字节
命令返回代码
2
字节
命令计数器
3
字节
该DAQ列表中ODT的数目
4
字节
该列表中第一个ODT表PID值
5-7
字节
填0(不关心)
UINT8pbCROData[8];
pbCROData[0] = CC_GET_DAQ_SIZE;
pbCROData[1] = m_bCTR ++;
pbCROData[2] = bListNum;
// don't care
pbCROData[3]= 0x00;
pbCROData[4] = (UINT8)(dwCANId >> 24);
pbCROData[5] = (UINT8)(dwCANId >> 16);
pbCROData[6] = (UINT8)(dwCANId >> 8);
pbCROData[7] = (UINT8)(dwCANId >> 0);
UINT8bRlt;
UINT8pbDTOData[8];
if (CRC_OK != (bRlt = SendPackage(pbCROData,pbDTOData, TRANSMIT_TIMEOUT))) {
return bRlt;
}
// Response
// 0 Packet ID: 0xFF
// 1 Command Return Code
// 2 Command Counter = CTR
// 3 DAQ list size (= number of ODTs in this list)
// 4 Fisrt PID of DAQ list
// 5..7 don't care
bDAQListSize = pbDTOData[3];
bFirstPID = pbDTOData[4];
return pbDTOData[1];
}
3.3.8SET_DAQ_PTR命令:
命令接收对象(CRO):
位(bit)
数据类型
描述
0
字节
命令代码(0x15)
1
字节
命令计数器
2
字节
DAQ表号(0,1…)
3
字节
QDT表号(0,1…)
4
字节
ODT表里的元素(0,1…)
5-7
字节
填0(不关心)
数据传送对象(DTO):
位(bit)
数据类型
描述
0
字节
命令代码(0xFF)
1
字节
命令返回代码
2
字节
命令计数器
3-7
字节
填0(不关心)
UINT8pbCROData[8];
pbCROData[0] = CC_SET_DAQ_PTR;
pbCROData[1] = m_bCTR ++;
pbCROData[2] = bListNum;
pbCROData[3] = bODTNum;
pbCROData[4] = bElementNum;
pbCROData[5]= 0x00;
pbCROData[6] = 0x00;
pbCROData[7] = 0x00;
UINT8bRlt;
UINT8pbDTOData[8];
if (CRC_OK != (bRlt = SendPackage(pbCROData,pbDTOData, TRANSMIT_TIMEOUT))) {
return bRlt;
}
// Response
// 0 Packet ID: 0xFF
// 1 Command Return Code
// 2 Command Counter = CTR
// 3..7 don't care
return pbDTOData[1];
3.3.9WTITE_DAQ命令:
命令接收对象(CRO):
位(bit)
数据类型
描述
0
字节
命令代码(0x16)
1
字节
命令计数器
2
字节
DAQ表中元素的长度(1,2,4)
3
字节
表中元素的扩展地址
4-7
字节
表中元素的地址
数据传送对象(DTO):
位(bit)
数据类型
描述
0
字节
命令代码(0xFF)
1
字节
命令返回代码
2
字节
命令计数器
3-7
字节
填0(不关心)
UINT8 pbCROData[8];
pbCROData[0] = CC_WRITE_DAQ;
pbCROData[1] = m_bCTR ++;
pbCROData[2] = bElementSize;
pbCROData[3] = bAddrExt;
pbCROData[4] = (UINT8)(dwAddr >> 24);
pbCROData[5] = (UINT8)(dwAddr >> 16);
pbCROData[6] = (UINT8)(dwAddr >> 8);
pbCROData[7] = (UINT8)(dwAddr >> 0);
UINT8bRlt;
UINT8pbDTOData[8];
if (CRC_OK != (bRlt = SendPackage(pbCROData,pbDTOData, TRANSMIT_TIMEOUT))) {
return bRlt;
}
// Response
// 0 Packet ID: 0xFF
// 1 Command Return Code
// 2 Command Counter = CTR
// 3..7 don't care
return pbDTOData[1];
3.3.10 START-STOP命令:
位(bit)
数据类型
描述
0
字节
命令代码(0x06)
1
字节
命令计数器
2
字节
停止:0x00;启动:0x01;准备:0x02
3
字节
DAQ 列表数
4
字节
该DAQ列表中最后一张ODT表数
5
字节
触发事件数
6-7
字
发送速率分频系数
数据传送对象(DTO):
位(bit)
数据类型
描述
0
字节
命令代码(0xFF)
1
字节
命令返回代码
2
字节
命令计数器
3-7
字节
填0(不关心)
UINT8 pbCROData[8];
pbCROData[0] = CC_START_STOP;
pbCROData[1] = m_bCTR ++;
pbCROData[2] = bMode;
pbCROData[3] = bDAQNum;
pbCROData[4] = bLastODTNum;
pbCROData[5] = bEventChannelNo;
pbCROData[6] = (UINT8)(wTransmissionRatePrescaler >> 8);
pbCROData[7] = (UINT8)(wTransmissionRatePrescaler >> 0);
UINT8bRlt;
UINT8pbDTOData[8];
if (CRC_OK != (bRlt = SendPackage(pbCROData,pbDTOData, TRANSMIT_TIMEOUT))) {
return bRlt;
}
// Response
// 0 Packet ID: 0xFF
// 1 Command Return Code
// 2 Command Counter = CTR
// 3..7 don't care
return pbDTOData[1];
3.3.11CLEAR_MEMORY命令:
命令接收对象(CRO):
位(bit)
数据类型
描述
0
字节
命令代码(0x10)
1-7
字节
填0(不关心)
数据传送对象(DTO):
位(bit)
数据类型
描述
0
字节
命令代码(0xFF)
1
字节
命令返回代码
2
字节
命令计数器
3-7
字节
填0(不关心)
3.3.12PROGRAM命令:
命令接收对象(CRO):
位(bit)
数据类型
描述
0
字节
命令代码(0x18)
1-7
字节
填0(不关心)
数据传送对象(DTO):
位(bit)
数据类型
描述
0
字节
命令代码(0xFF)
1
字节
命令返回代码
2
字节
命令计数器
3-7
字节
填0(不关心)
4、标定实现(举例)
建立完善的匹配标定具体流程为:与底层ECU进行连接,监控、在线标定,上载和下载map图,断开连接等操作。对于匹配标定的2个最主要的任务,就是在线标定和实时监控,它是通过协议命令的组合,来实现的,下面举例说明如何实现:
4.1监控命令解析:(假设有n张DAQ列表,每张列表中有m张ODT表)
序号
上位机
CCP
CAN
备注
1
设置监控变量列表,选择采样速率
(.A2L)
2
GET_DAQ_SIZE
发送
重复n次
3
CRM-DTO
接收
重复n次
4
SET_DAQ_PTR
发送
list 0~list m-1
5
CRM-DTO
接收
list 0~list m-1
6
WRITE_DAQ
发送
list 0~list m-1
7
CRM-DTO
接收
list 0~list m-1
8
START_STOP
发送
list 0~list n-1
9
CRM-DTO
接收
list 0~list n-1
10
START_STOP_ALL
发送
开始监控
11
CRM-DTO
接收
12
DAQ-DTO
接收
接收多次
13
显示
解码显示
14
START_STOP_ALL
发送
停止显示
15
CRM-DTO
接收
4.2 在线标定
标号
上位机
CCP
CAN
备注
1
修改数据
可能有n次
2
SET_MTA
发送
3
CRM-DTO
接收
4
DNLOAD
发送
5
CRM-DTO
接收
6
SHORT_UP
发送
7
CRM-DTO
接收
SETMTA 命令:
UINT8SetMTA(UINT8 bMTANumber, UINT8 bAddrExt, UINT32 dwAddr) {
UINT8pbCROData[8];
pbCROData[0]= CC_SET_MTA;
pbCROData[1] = m_bCTR ++;
pbCROData[2] = bMTANumber;
pbCROData[3] = bAddrExt;
pbCROData[4] = (UINT8)(dwAddr >> 24);
pbCROData[5] = (UINT8)(dwAddr >> 16);
pbCROData[6] = (UINT8)(dwAddr >> 8);
pbCROData[7] = (UINT8)(dwAddr >> 0);
UINT8bRlt;
UINT8pbDTOData[8];
// if (CRC_OK != (bRlt = SendMessage(pbCROData, pbDTOData,TRANSMIT_TIMEOUT))) {
if (CRC_OK != (bRlt = SendPackage(pbCROData,pbDTOData, 2000))) {
return bRlt;
}
// Response
// 0 Packet ID: 0xFF
// 1 Command Return Code
// 2 Command Counter = CTR
// 3..7 don't care
return pbDTOData[1];
}
- 基于CCP协议的CAN总线
- 基于CCP协议的CAN总线
- 基于CAN总线的匹配标定协议
- 基于.net2.0的汽车电子CCP协议的封装
- ccp协议
- CCP协议
- 基于CAN总线的汽车诊断协议UDS (网络层 ISO 15765)
- 基于C的CAN总线切换方案
- 基于CPLD的CAN总线设计
- 基于stm32的can总线彻底研究
- 基于can总线节点ECU的设计
- 基于stm32的can总线彻底研究
- 基于stm32的can总线彻底研究
- 基于树莓派3的CAN总线编程
- 基于LPC2194的四路CAN总线通信
- 基于C8051F040单片机的CAN总线通信
- 基于CAN总线的实验室管理系统
- CAN总线协议
- 2014.8.2模拟赛【果实计数】
- poj 3421 X-factor Chains(分解质因数+组合数学)
- [LeetCode] Maximum Subarray
- PHP 登录TPlink路由器
- 手机sso.
- 基于CCP协议的CAN总线
- php中POST请求
- 关于iphone开发中的@property和@synthesize的一些见解
- 最短路径
- Jtemplates 基本语法
- TCP带外数据测试
- 2014-08-02 日志
- 对于 MVVM 我想说:自已的事情自已做,控制器就简化了!
- HDU 1829 A Bug's Life (并査集)