CANopen协议开发梳理总结笔记教程

0、提醒

        CANOpen使用时,需要清楚什么是大端和小端,这对于CANOpen数据发送及解析时,有很大的帮助。且学习开发CANOpen时,需要具备一定的CAN基础。

1、CANOpen协议介绍

①、什么是CANOpen协议

        CANOpen协议是一种架构在控制局域网络(Controller Area Network, CAN)上的高层通信协议,它广泛应用于工业自动化、机械工程和汽车电子等领域。CANOpen协议通过对象字典、服务数据对象(SDO)、过程数据对象(PDO)等机制,为机器人、运动控制、过程控制、楼宇自动化、交通运输等行业提供了一种标准化的通信解决方案。

        CANOpen协议的标准由非营利组织CiA(CAN in Automation)进行起草、审核及维护工作。

        CANOpen协议本身是一个单一的标准,它定义了设备间的通信协议和接口规范。

        CANOpen协议支持从10kbps到1Mbps的波特率,具体包括10k、20k、50k、125k、250k、500k、800k和1Mbps。

        简单来说,CANOpen协议是一个基于CAN协议的的一个应用层协议。

②、CANOpen协议的特性

        开放性:CANOpen是一个公开的标准,任何公司都可以使用它来开发产品,无需支付许可费用。

        网络管理:CANOpen协议定义了网络管理功能,如节点自诊断、网络监控等,使得网络维护更加方便。

        对象字典:CANOpen使用对象字典来描述设备的功能和状态,使得设备之间的通信更加标准化。

        服务:CANOpen定义了一系列的服务,如NMT(Network Management)、TPDO(Time-Triggered Protocol Data Object)、RPDO(Real-Time Protocol Data Object)等,以满足不同的应用需求。

        PDO(Process Data Object):PDO是CANOpen中用于快速传输过程数据的数据对象,可以实时地传输控制和状态信息。

        SDO(Service Data Object):SDO用于访问设备的对象字典,可以读取或写入设备的状态和配置信息。

        紧急消息:CANOpen还定义了紧急消息,用于在发生严重故障时立即通知网络中的其他设备。

        心跳消息:心跳消息用于监测网络中设备的运行状态,如果一段时间内没有收到某个设备的心跳消息,网络管理系统会认为该设备已经离线。

        CANOpen常用缩写

③、CANOpen协议应用场景

        在CANOpen协议中,对于不同类型的CANopen 设备和应用场景分别有不同的子协议,如CiA301、CiA401、CiA402、CiA421、CiA423、CiA424、CiA426、CiA430、CiA433等众多子协议构成了CANopen协议。

2、CANOpen字典

        CANOpen字典(Object Dictionary, OD)是CANopen协议的核心组成部分,它是一个有序的对象组,用于描述CANopen节点的所有参数,包括通讯数据的存放位置。

        CANOpen字典的结构由索引和子索引组成:

        索引:每个对象采用一个16位的索引值来寻址,范围在0x0000到0xFFFF之间。

        子索引:在某些索引下,为了访问数据结构中的单个元素,定义了一个8位的子索引,范围是0x00到0xFF之间。

        CANOpen的SDO模式下的数据传输时,也是按如下格式进行发送和接收。其中字典中的部分索引可能没有子索引。

3、CANOpen通信

        CANOpen通信有两种模式,分别是SDO通信、和PDO通信,如下图所示为CANOpen通信的设备模型图。

①、SDO通信

        SDO 全称为服务数据对象,其通过对象索引和子索引与CANOpen字典建立联系,通过SDO可以读取对象数据,在允许的情况下,也可以修改写入对象数据。

        SDO 传输方式遵循客户端—服务器模式(CS),即一应一答方式。由 CAN 总线网络中的 SDO 客户端发起,SDO 服务器作出应答。

        SDO 传输报文由COB-ID数据段组成,数据段采用小端模式,即低位在前,高位在后排列。所有的 SDO 报文数据段都必须是 8 个字节。

        SDO发送数据的COB-ID都是0x600+节点ID

        SDO接收数据的COB-ID都是0x580+节点ID

SDO读数据报文格式

SDO写数据报文格式

②、PDO通信

        PDO 全称为 过程数据对象, 其用来传输实时的数据,是 CANopen 中最主要的数据传输方式。通过SDO配置PDO后,可以实现设备端的数据周期性自动上传到服务器,也可以实现控制发送的数据小于8字节,由于PDO发送的数据无返回,因此可以极大的提升数据传输速度。

        按照接收与发送的不同,PDO又分为TPDO和RPDO,其中RPDO用于服务器给设备端发送控制数据TPDO为设备端周期性上传数据到服务器

        PDO 的传输遵循的是生产者消费者模型,即 CAN 总线网络中生产者产生的 TPDO 可根据COB-ID 由网络上一个或者多个消费者 RPDO 接收。每个PDO由通信参数和映射参数共同决定最终传输的方式及内容。

        如下是所使用的电机控制器中实现 PDO 的传输的4 个 RPDO 和4 个 TPDO。注意,不同控制器的PDO数量可能不一致,需要根据实际产品进行手册参考。

        PDO使用时,需要进行映射配置操作,如下所示为PDO映射操作的流程图。

        因PDO映射内容较多,因此将在下一篇博客中详细介绍PDO映射操作。

3、CANOpen应用

①、设置CiA402模式

        发送:601 2B 02 20 01 00 00 00 00 (设置为 CiA402 模式)

//2B 02 20 01 00 00 00 00   (CiA402 模式)
#define WRITE_2_BYTE        0x2B
#define WRITE_60_CTRL_PARAM 0x2002
#define CTRL_MODE_SELECT    0x01
#define CIA402_MODE         0x00

//将数据按规定填充到CAN的8字节数据区
char data[8] = { 0 };
data[0] = WRITE_2_BYTE;
data[1] = WRITE_60_CTRL_PARAM & 0xFF;
data[2] = WRITE_60_CTRL_PARAM >> 8 & 0xFF;
data[3] = CTRL_MODE_SELECT;
data[4] = CIA402_MODE;

serve_motor_send_data(0x601, data);
//成功会返回数据:60 02 20 01 00 00 00 00 

②、循环同步位置模式

        发送:601 2F 60 60 00 08 00 00 00 (循环同步位置模式)

//2F 60 60 00 08 00 00 00 (循环同步位置模式)
#define WRITE_1_BYTE         0x2F   
#define WRITE_60_RUN_MODE    0x6060
#define CYCLIC_SYNC_POS_MODE 0x08

//将数据按规定填充到CAN的8字节数据区
char data[8] = {0};   
data[0] = WRITE_1_BYTE;
data[1] = WRITE_60_RUN_MODE & 0xFF;
data[2] = WRITE_60_RUN_MODE >> 8 & 0xFF;
data[3] = 0x00;
data[4] = CYCLIC_SYNC_POS_MODE;

serve_motor_send_data(0x601, data);
//成功会返回数据: 60 60 60 00 00 00 00 00 

③、电机准备

        发送: 601 2B 40 60 00 06 00 00 00 (设置 6040h为 0x6, 使电机准备)

//2B 40 60 00 06 00 00 00
#define WRITE_2_BYTE           0x2B
#define WRITE_60_CTRL_STATE    0x6040
#define MOTOR_READY            0x06

//将数据按规定填充到CAN的8字节数据区
char data[8] = { 0 };
data[0] = WRITE_2_BYTE;
data[1] = WRITE_60_CTRL_STATE & 0xFF;
data[2] = WRITE_60_CTRL_STATE >> 8 & 0xFF;
data[3] = 0x00;
data[4] = MOTOR_READY;

servo_motor_send_data(0x601, data);
//正常会返回数据:60 40 60 00 00 00 00 00 

③、电机锁轴使能

        发送: 601 2B 40 60 00 0F 00 00 00 (设置 6040h为 0xF, 使电机使能)

//2B 40 60 00 0F 00 00 00
#define WRITE_2_BYTE          0x2B
#define WRITE_60_CTRL_STATE   0x6040 
#define MOTOR_ENABLE          0x7F

 //将数据按规定填充到CAN的8字节数据区
char data[8] = { 0 };
data[0] = WRITE_2_BYTE;
data[1] = WRITE_60_CTRL_STATE & 0xFF;
data[2] = WRITE_60_CTRL_STATE >> 8 & 0xFF;
data[3] = 0x00;
data[4] = MOTOR_ENABLE;

servo_motor_send_data(0x601, data);
//正常会返回数据:60 40 60 00 00 00 00 00 

④、电机松轴失能

        发送: 601 2B 40 60 00 07 00 00 00 (设置 6040h为 0x7, 使电机失能)

//2B 40 60 00 07 00 00 00
#define WRITE_2_BYTE           0x2B
#define WRITE_60_CTRL_STATE    0x6040    
#define MOTOR_DISABLE          0x07

//将数据按规定填充到CAN的8字节数据区
char data[8] = { 0 };
data[0] = WRITE_2_BYTE;
data[1] = WRITE_60_CTRL_STATE & 0xFF;
data[2] = WRITE_60_CTRL_STATE >> 8 & 0xFF;
data[3] = 0x00;
data[4] = MOTOR_DISABLE;

servo_motor_send_data(0x601, data);
//正常会返回数据:60 40 60 00 00 00 00 00 

⑤、设置电机目标位置

        发送: 601 23 7A 60 00 10 27 00 00 (设置目标位置 607Ah为 10000)

//目标位置    :   23 7A 60 00 10 27 00 00 (设置 607Ah为 10000)
#define WRITE_4_BYTE         0x23   
#define WRITE_60_POSITION    0x607A

int pos = 90;//90度
int pos_pulse = (int)(pos * 10000.0 / 360);//数值单位转换(角度值数据转换为脉冲)
char data[8] = { 0 };

//将数据按规定填充到CAN的8字节数据区
data[0] = WRITE_4_BYTE;
data[1] = WRITE_60_POSITION & 0xFF;
data[2] = WRITE_60_POSITION >> 8 & 0xFF;
data[3] = 0x00;
data[4] = pos_pulse & 0xFF;
data[5] = pos_pulse >> 8 & 0xFF;
data[6] = pos_pulse >> 16 & 0xFF;
data[7] = pos_pulse >> 24 & 0xFF;

servo_motor_send_data(0x601, data);
//正常会返回到数据
//例如:60 7A 60 00 00 00 00 00 

⑥、读取电机实际位置

        发送:601 40 63 60 00 00 00 00 00

#define READ_60_CMD      0x40
#define READ_60_POSITION 0x6063

//将数据按规定填充到CAN的8字节数据区
char data[8] = { 0 };
data[0] = READ_60_CMD;
data[1] = READ_60_POSITION & 0xFF;
data[2] = READ_60_POSITION >> 8 & 0xFF;

servo_motor_send_data(0x601, data);
//正常会返回到读取到的位置数据
//例如:43 63 60 00 F1 2D C0 01 

⑦、读取电机实际速度

        发送:601 40 6C 60 00 00 00 00 00

//40 6C 60 00 00 00 00 00
#define READ_60_CMD    0x40
#define READ_60_SPEED  0x606C

//将数据按规定填充到CAN的8字节数据区
char data[8] = { 0 };
data[0] = READ_60_CMD;
data[1] = READ_60_SPEED & 0xFF;
data[2] = READ_60_SPEED >> 8 & 0xFF;

servo_motor_send_data(0x601, data);
//正常会返回到读取到的速度数据
//例如:43 6C 60 00 7C F6 FF FF 

⑧、读取电机实际电流

        发送:601 40 78 60 00 00 00 00 00

//40 78 60 00 00 00 00 00
#define READ_60_CMD 0x40
#define READ_60_CURRENT 0x6078

//将数据按规定填充到CAN的8字节数据区
char data[8] = { 0 };
data[0] = READ_60_CMD;
data[1] = READ_60_CURRENT & 0xFF;
data[2] = READ_60_CURRENT >> 8 & 0xFF;

servo_motor_send_data(0x601, data);
//正常会返回到读取到的电流数据
//例如:4B 78 60 00 FC FF 00 00 

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.mfbz.cn/a/781925.html

如若内容造成侵权/违法违规/事实不符,请联系我们进行投诉反馈qq邮箱809451989@qq.com,一经查实,立即删除!

相关文章

yaml格式转换成json格式

yaml格式转换成json格式 ①postman生成的结果是yaml格式 ps:postman输出的格式是没有自动换行的,需要将内容换行 ②复制到Python的脚本跑一趟:自动换行并去掉/n; str " "//(postman输出的内容) print(st…

【python技巧】parser传入参数

参考网址: https://lightning.ai/docs/pytorch/LTS/api/pytorch_lightning.utilities.argparse.html#pytorch_lightning.utilities.argparse.add_argparse_args 1. 简单传入参数. parse_known_args()方法的作用就是把不在预设属性里的参数也返回,比如下面这个例子, 执行pytho…

2024年信息系统项目管理师1批次上午客观题参考答案及解析(1)

1、新型基础设施建设是以新发展理念为引领,以()为驱动,以信息网络为基础,面向高质量发展需要,提供数字转型、智能升级、融合创新等服务的基础设施体系。 A.技术创新 B.人工智能 C.区块链 D&…

代码随想录算法训练营第二十七天|452. 用最少数量的箭引爆气球、435. 无重叠区间、763.划分字母区间

452. 用最少数量的箭引爆气球 如何使用最少的弓箭呢? 直觉上来看,貌似只射重叠最多的气球,用的弓箭一定最少,那么有没有当前重叠了三个气球,我射两个,留下一个和后面的一起射这样弓箭用的更少的情况呢&am…

STM32-输入捕获IC和编码器接口

本内容基于江协科技STM32视频学习之后整理而得。 文章目录 1. 输入捕获IC1.1 输入捕获IC简介1.2 频率测量1.3 输入捕获通道1.4 主从触发模式1.5 输入捕获基本结构1.6 PWMI基本结构 2. 输入捕获库函数及代码2.1 输入捕获库函数2.2 6-6 输入捕获模式测频率2.2.1 硬件连接2.2.2 硬…

曹操的五色棋布阵 - 工厂方法模式

定场诗 “兵无常势,水无常形,能因敌变化而取胜者,谓之神。” 在三国的战场上,兵法如棋,布阵如画。曹操的五色棋布阵,不正是今日软件设计中工厂方法模式的绝妙写照吗?让我们从这个神奇的布阵之…

MSPM0G3507——串口0从数据线传输变为IO口传输

默认的跳线帽时这样的,这样时是数据线传输 需要改成这样,即可用IO口进行数据传输

实验六 图像的傅立叶变换

一.实验目的 1了解图像变换的意义和手段; 2熟悉傅立叶变换的基本性质; 3熟练掌握FFT变换方法及应用; 4通过实验了解二维频谱的分布特点; 5通过本实验掌握利用MATLAB编程实现数字图像的傅立叶变换。 6评价人眼对图…

Mac 系统如何将搜狗输入法设置为默认输入法

Mac 系统默认将自带的ABC输入法作为默认输入法,很不方便中文输入,想设置搜狗输入法为默认输入法如何设置呢?具体步骤如下: 1、打开:系统设置——键盘——文字输入,点击设置 2、点击左下角的 3、选择 其他…

52-5 内网代理2 - LCX端口转发(不推荐使用LCX)

环境搭建: 本地开3台虚拟机:kali(必须)、windows2012与2008 (可换成其他windows虚拟机) kali - 网络配置成桥接模式 windows2012 - 设置两个网卡,NAT与桥接模式 注意:windows2012要关闭防火墙,要不然其他主机ping不通 关闭防火墙后再开启远程桌面连接 windwos20…

Java项目:基于SSM框架实现的德云社票务管理系统【ssm+B/S架构+源码+数据库+开题报告+毕业论文】

一、项目简介 本项目是一套基于SSM框架实现的德云社票务管理系统 包含:项目源码、数据库脚本等,该项目附带全部源码可作为毕设使用。 项目都经过严格调试,eclipse或者idea 确保可以运行! 该系统功能完善、界面美观、操作简单、功…

Python 学习中什么是字典,如何操作字典?

什么是字典 字典(Dictionary)是Python中的一种内置数据结构,用于存储键值对(key-value pair)。字典的特点是通过键来快速查找值,键必须是唯一的,而值可以是任何数据类型。字典在其他编程语言中…

游戏AI的创造思路-技术基础-遗传算法

遗传算法,选对了遗传算子,那就是优秀的继承者,选错了,那就是传说在祸害遗千年~~~~~ 目录 1. 定义 2. 发展历史 3. 遗传算法的基本原理和流程 3.1. 基本原理 3.1.1.基本原理 3.1.2. 算法流程 3.1.3. 关键要素 3.2. 函数和方…

栈和队列---循环队列

1.循环队列的出现 (1)上面的这个就是一个普通的数据的入队和出队的过程我们正常情况下去实现这个入队和出队的过程,就是这个数据从这个队尾进入,从队头离开,但是这个加入的时候肯定是没有其他的问题的,直接…

为什么固定尺寸 AdSense 广告依旧会出现并非指定的尺寸广告?

经常在网站上投放谷歌 AdSense广告的站长应该都碰到过,明明投放的是固定尺寸的广告位里旧会出现并非指定尺寸的AdSense 广告,很诡异的感觉。其实这都是因为你的 AdSense 账号广告优化造成的,其中里面就包含了广告尺寸优化,只需要在…

盘点当下智能体应用开发的几种形态

现在多智能体系统开发的关注度越来越高了,不光在开发者的圈子热度很高,很多职场人士,甚至是小白也参与其中,因为现在的门槛越来越低了,尤其是,最近特别火的扣子(coze)和百度的appbui…

Sequelize 操作 MySQL 数据库

安装 npm install --save sequelize安装驱动程序: npm install --save mysql2连接到数据库 要连接到数据库,必须创建一个 Sequelize 实例. 这可以通过将连接参数分别传递到 Sequelize 构造函数或通过传递一个连接 URI 来完成: const {Sequelize} re…

【Java12】封装

封装(Encapsulation)是面向对象的三大特征之一(另两个是继承和多态),指的是将对象的状态信息隐藏在对象内部,不允许外部程序直接访问对象的内部信息,而是通过该类所提供的方法来实现对内部信息的…

[护网训练]原创应急响应靶机整理集合

前言 目前已经出了很多应急响应靶机了,有意愿的时间,或者正在准备国护的师傅,可以尝试着做一做已知的应急响应靶机。 关于后期: 后期的应急响应会偏向拓扑化,不再是单单一台机器,也会慢慢完善整体制度。…

《昇思25天学习打卡营第14天|onereal》

第14天学习内容如下: Diffusion扩散模型 本文基于Hugging Face:The Annotated Diffusion Model一文翻译迁移而来,同时参考了由浅入深了解Diffusion Model一文。 本教程在Jupyter Notebook上成功运行。如您下载本文档为Python文件&#xff0c…