发新帖我要提问
123
返回列表
打印
[资料分享]

Stellaris CAN 模块 控制器局域网(CAN)

[复制链接]
楼主: 米多0036
手机看帖
扫描二维码
随时随地手机跟帖
41
米多0036|  楼主 | 2020-4-28 13:14 | 只看该作者 回帖奖励 |倒序浏览
CANIntStatus
返回 CAN 控制器当前中断状态。
函数原型:
unsigned long
CANIntStatus(unsigned long ulBase,
tCANIntStsReg eIntStsReg)
参数:
ulBase 是 CAN 控制器的基址。
eIntStsReg 表示要读取哪一个中断状态寄存器。
描述:
返回二个中断状态寄存器的其中一个值。读中断状态寄存器是由 eIntStsReg 参数决定,
它是下列值中的其中之一:
z CAN_INT_STS_CAUSE – 表示中断产生的原因;
z CAN_INT_STS_OBJECT – 表示正在挂起全部报文对象的中断。
CAN_INT_STS_CAUSE 返回控制器中断寄存器的值并表示中断产生的原因。如果原因
是一个状态中断,那么它将是 CAN_INT_INTID_STATUS 的一个值。在这种情况下,应该
使用 CANStatusGet()函数读取状态寄存器。调用此函数读取状态寄存器也将会清除状态中
断。如果中断寄存器的值处于 1-32 之间,那么即表示具有高优先级编号的报文对象正在挂
起一个中 断。通过 使 用 CANIntClear() 函 数 ,或在一 个接收到 的报文情 况下使用
CANMessageGet()读取报文,就能清除报文对象中断。中断处理程序能再次读取中断状态,
以确保在中断返回前清除全部挂起的中断。
CAN_INT_STS_OBJECT 返回一个表示报文对象正在挂起中断的位屏蔽。这就能立即发现全部挂起的中断,而无需使用 CAN_INT_STS_CAUSE 重复读取中断寄存器。
返回:
返回中断状态寄存器中的一个值。

使用特权

评论回复
42
米多0036|  楼主 | 2020-4-28 13:14 | 只看该作者
CANIntUnregister
注销一个 CAN 控制器的中断处理程序。
函数原型:
void
CANIntUnregister(unsigned long ulBase)
参数:
ulBase 是 CAN 控制器的基址。
描述:
此函数把以前注册的中断处理程序注销并禁止中断控制器的中断。
也可参考:
有关注册中断处理程序的重要信息,请参考 IntRegister()。
返回:
无。

使用特权

评论回复
43
米多0036|  楼主 | 2020-4-28 13:15 | 只看该作者
CANMessageClear
清除一个不再使用的报文对象。
函数原型:
void
CANMessageClear(unsigned long ulBase,
unsigned long ulObjID)
参数:
ulBase 是 CAN 控制器的基址。
ulObjID 是要禁止的报文对象编号(1-32)。
描述:
此函数清除一个不再使用的特定的报文对象。一旦一个报文对象已被“清除”,那么它
将不能再自动地发送或接收报文,或产生中断。
返回:
无。

使用特权

评论回复
44
米多0036|  楼主 | 2020-4-28 13:15 | 只看该作者
CANMessageGet
读取其中一个报文对象缓冲区的 CAN 报文。
函数原型:
void
CANMessageGet(unsigned long ulBase,
unsigned long ulObjID,
tCANMsgObject *pMsgObject,
tBoolean bClrPendingInt)
参数:
ulBase 是 CAN 控制器的基址。
ulObjID 是要读取的对象编号(1-32)。
pMsgObject 指向一个包含报文对象段的结构。
bClrPendingInt 表示是否应该清除一个相关的中断。
描述:
此函数一般读取 CAN 控制器的 32 个报文对象中的其中之一的内容,并把它返回给调
用者。返回的数据被存放在 pMsgObject 所指向的,由调用者提供的结构的段(fields)中。
此数据由 CAN 报文所有组成部分再加上一些控制和状态信息构成。
通常此函数是读取接收的到和存放着一个带有某个标识符的 CAN 报文的报文对象。但是,
它也能用来读取报文对象的内容,以防在只需要对上一次设置的结构进行部分更改时能装载结构
段。
当使用 CANMessageGet 时,全部结构的相同段是以使用 CANMessageSet()函数那样的
相同方式定位,以下除外:
pMsgObject->ulFlags:
z MSG_OBJ_NEW_DATA 表示自从上一次读取后,这是否是新数据。
z MSG_OBJ_DATA_LOST 表示至少在这个报文对象中接收到一个报文,并且在被覆
写前不被主机读取。
返回:
无。

使用特权

评论回复
45
米多0036|  楼主 | 2020-4-28 13:17 | 只看该作者
CANMessageSet
配置 CAN 控制器的一个报文对象。
函数原型:
void
CANMessageSet(unsigned long ulBase,
unsigned long ulObjID,
tCANMsgObject *pMsgObject,
tMsgObjType eMsgType)
参数:
ulBase 是 CAN 控制器的基址。
ulObjID 是要配置的对象编号(1-32)。
pMsgObject 是指向一个包含报文对象设置的结构的指针。
eMsgType 表示这个对象的报文类型。
描述:
此函数一般对 CAN 控制器的 32 个报文对象中的任何一个报文对象进行配置。一个报
文对象能被配置成 CAN 报文对象的任何类型和自动发送和接收的几个选项。此次调用允许
报文对象被配置可以在接收完或发送完报文时产生中断。报文对象也能被配置成具有一个过
滤器/屏蔽,所以只有符合某参数的报文在 CAN 总线上被发现时才执行操作。
eMsgType 参数必须是下列值中的一个:
-MSG_OBJ_TYPE_TX – CAN 发送报文对象;
-MSG_OBJ_TYPE_TX_REMOTE – CAN 发送远程请求报文对象;
-MSG_OBJ_TYPE_RX – CAN 接收报文对象;
-MSG_OBJ_TYPE_RX_REMOTE – CAN 接收远程请求报文对象;
-MSG_OBJ_TYPE_RXTX_REMOTE – CAN 远程帧接收远程,然后发送报文对象。
pMsgObject 所指向的报文对象必须由调用者来定位,如下:
-ulMsgID – 包含报文 ID,11 位或 29 位;
-ulMsgIDMask – 如果标识符过滤使能,ulMsgID 的位屏蔽必须匹配;
-ulFlags;
♦ 设置 MSG_OBJ_TX_INT_ENABLE 标志,以使能发送时的中断;
♦ 设置 MSG_OBJ_RX_INT_ENABLE 标志,以使能接收时的中断;
♦ 设置 MSG_OBJ_USE_ID_FILTER 标志,以使能基于 ulMsgIDMask 所指定的标
识符屏蔽的过滤。
-ulMsgLen – 报文数据的字节数。对于一个远种帧而言,这应该是一个非零的偶数;
它应该与响应数据帧的期望数据字节匹配;
-pucMsgData – 指向一个包多达 8 个数据字节的数据帧的缓冲区。

使用特权

评论回复
46
米多0036|  楼主 | 2020-4-28 13:18 | 只看该作者
为了直接把一个数据帧或远程帧发送出去,要执行下列步骤:
1 把 tMsgObjType 设置为 MSG_OBJ_TYPE_TX。
2 把 ulMsgID 设为报文 ID。
3 设置 ulFlags,设置 MSG_OBJ_TX_INT_ENABLE,以便在发送报文时获取一个中断。
为了禁止基于报文标识符的过滤,一定不要设置 MSG_OBJ_USE_ID_FILTER。
4 把 ulMsgLen 设置为数据帧的字节数。
5 把 pucMsgData 设置为指向一个包含报文字节的数组(如果是一个数据帧,不适用此
操作;如果是一个远程帧,把这设置为指向一个有效缓冲区则是一个好方法)。
6 调用此函数,并把 ulObjID 设置为 32 个对象缓冲区中的其中一个缓冲区。
为了接收一个特定的数据帧,要执行下列步骤:
1 把 tMsgObjType 设置为 MSG_OBJ_TYPE_RX。
2 把 ulMsgID 设为完整报文 ID,或使用部分 ID 匹配的部分屏蔽。
3 设置 ulMsgIDMask 位,用于在对比过程中的屏蔽。
4 按如下设置 ulFlags:
♦ 设置 MSG_OBJ_TX_INT_ENABLE 标志,以便在接收数据帧时被中断;
♦ 设置 MSG_OBJ_USE_ID_FILTER 标志,以便使能基于过滤的标识符。
5 把 ulMsgLen 设置为期望数据帧的字节数。
6 此次调用并不使用 pucMsgData 所指向的缓冲区。
6 调用此函数,并把 ulObjID 设置为 32 个对象缓冲区中的其中一个缓冲区。
如果您指定的报文对象缓冲区已包含有一个报文标识符,那么它将会被覆写。
返回:

使用特权

评论回复
47
米多0036|  楼主 | 2020-4-28 13:18 | 只看该作者
CANRetryGet
返回自动重发的当前设置。
函数原型:
tBoolean
CANRetryGet(unsigned long ulBase)
参数:
ulBase 是 CAN 控制器的基址。
描述:
读取 CAN 控制器中的自动重发的当前设置,并把它返回给调用者。
返回:
如果使能自动重发,返回 True,否则返回 False。

使用特权

评论回复
48
米多0036|  楼主 | 2020-4-28 13:19 | 只看该作者
CANRetrySet
设置 CAN 控制器自动重发操作。
函数原型:
void
CANRetrySet(unsigned long ulBase,
tBoolean bAutoRetry)
参数:
ulBase 是 CAN 控制器的基址。
bAutoRetry 使能自动重发。
描述:
使能或禁止含有检测错误报文的自动重发。如果 bAutoRetry 为 True,那么使能自动重
发,否则将其禁止。
返回:
无。

使用特权

评论回复
49
米多0036|  楼主 | 2020-4-28 13:20 | 只看该作者
CANStatusGet
读取其中一个控制器状态寄存器。
函数原型:
unsigned long
CANStatusGet(unsigned long ulBase,
tCANStsReg eStatusReg)
参数:
ulBase 是 CAN 控制器的基址。
eStatusReg 是要读的状态寄存器。
描述:
读取 CAN 控制器中的一个状态寄存器,并把它返回给调用者。不同的状态寄存器为:
-CAN_STS_CONTROL – 主控制器状态;
-CAN_STS_TXREQUEST – 挂起发送对象的位屏蔽;
-CAN_STS_NEWDAT –具有新数据的对象的位屏蔽;
-CAN_STS_MSGVAL – 含有有效配置的对象的位屏蔽。
在读取主控制器状态寄存器时,将清除一个正在挂起的状态中断。如果原因是一个状态
中断,那么就应该在 CAN 控制器的中断处理程序中使用此操作。控制器状态寄存器段如下
所示:
-CAN_STATUS_BUS_OFF – 控制器处于总线关闭条件;
-CAN_STATUS_EWARN – 一个错误计数器已达到了至少为 96 的限值;
-CAN_STATUS_EPASS – CAN 控制器处于错误被动状态;
-CAN_STATUS_RXOK –成功地接收到一个报文(独立于任何报文过滤);
-CAN_STATUS_TXOK – 成功地发送一个报文;
-CAN_STATUS_LEC_MSK – 最后错误代码位屏蔽(3 位);
-CAN_STATUS_LEC_NONE – 无错误;
-CAN_STATUS_LEC_STUFF – 检测到填充错误;
-CAN_STATUS_LEC_FORM – 报文的固定格式部分发生一个格式错误;
-CAN_STATUS_LEC_ACK – 一个发送的报文不被应答;
-CAN_STATUS_LEC_BIT1 – 当尝试在隐性模式(recessive mode)下发送时,检
测到一个显性电平(dominant level);
-CAN_STATUS_LEC_BIT0 –当尝试在显性模式(dominant mode)下发送时,检测
到一个隐性电平(recessive level);
-CAN_STATUS_LEC_CRC – CRC – 在所接收到报文中的 CRC 错误。
余下的状态寄存器是报文对象的 32 位位映射。使用它们就能快速得到全部报文对象的
状态信息,而无需单独询问每一个状态寄存器。它们包含下列信息:
-CAN_STS_TXREQUEST – 如果一个报文对象的 TxRequest 位被设,这就意味着这
个对象的发送正在挂起。应用能使用这个信息确定哪些对象仍在等待着发送一个报
文;
-CAN_STS_NEWDAT – 如果一个报文对象的 NewDat 位被设,这就意味着已接收
到这个对象的新报文,且并未被主应用程序挑选到;
-CAN_STS_MSGVAL – 如果一个报文对象的 MsgVa 位被设,这就意味着它已编程
一个有效的配置。主应用程序能使能此信息来确定哪些报文对象是空的/未被使用
的。
返回:
返回状态寄存器的值。

使用特权

评论回复
50
米多0036|  楼主 | 2020-4-28 13:22 | 只看该作者
编程示例
这个示例代码将把 CAN 控制器 0 的数据发送到 CAN 控制器 1 中。为了能实际上接收
到数据,必须在这二个端口之间连接一个外部电缆。在这个示例中,二个控制器都被配置为
具有 1Mbit 的操作速率。

使用特权

评论回复
51
米多0036|  楼主 | 2020-4-28 13:23 | 只看该作者
tCANBitClkParms CANBitClk;
tCANMsgObject sMsgObjectRx;
tCANMsgObject sMsgObjectTx;
unsigned char ucBufferIn[8];
unsigned char ucBufferOut[8];
//
// 把全部报文对象的状态和 CAN 模块的状态复位为一个已知状态
//
CANInit(CAN0_BASE);
CANInit(CAN1_BASE);
//
// 把控制器配置为具有 1 Mbit 的操作速率
//
CANBitClk.uSyncPropPhase1Seg = 5;
CANBitClk.uPhase2Seg = 2;
CANBitClk.uQuantumPrescaler = 1;
CANBitClk.uSJW = 2;
CANSetBitTiming(CAN0_BASE, &CANBitClk);
CANSetBitTiming(CAN1_BASE, &CANBitClk);
//
// 使 CAN0 器件不处于 INIT 状态
//
CANEnable(CAN0_BASE);
CANEnable(CAN1_BASE);
//
// 配置一个接收对象
//
sMsgObjectRx.ulMsgID = (0x400);
sMsgObjectRx.ulMsgIDMask = 0x7f8;
sMsgObjectRx.ulFlags = MSG_OBJ_USE_ID_FILTER;
sMsgObjectRx.ulMsgLen = 8;
sMsgObjectRx.pucMsgData = ucBufferIn;
CANMessageSet(CAN1_BASE, 1, &sMsgObjectRx, MSG_OBJ_TYPE_RX);
//
// 配置并启动报文对象发送
//
sMsgObjectTx.ulMsgID = 0x400;
sMsgObjectTx.ulFlags = 0;
sMsgObjectTx.ulMsgLen = 8;
sMsgObjectTx.pucMsgData = ucBufferOut;
CANMessageSet(CAN0_BASE, 2, &sMsgObjectTx, MSG_OBJ_TYPE_TX);
//
// 等待新数据变为可用
//
while((CANStatusGet(CAN1_BASE, CAN_STS_NEWDAT) & 1) == 0)
{
//
// 把报文对象的报文读出
//
CANMessageGet(CAN1_BASE, 1, &sMsgObjectRx, true);
}
//
// 处理在 sMsgObjectRx.pucMsgData 中的数据
//
...

使用特权

评论回复
发新帖 我要提问
您需要登录后才可以回帖 登录 | 注册

本版积分规则