【STM32cubeMX+HAL库】RS485双机通讯

【STM32cubeMX+HAL库】RS485双机通讯

一、原理篇

1.1、485简介(来源于正点原子官方手册)

485(一般称作RS485/ELA-485)隶属于OSI模型物理层,是串行通讯的一种。电气特性规定
为2线,半双工,多点通信的类型。它的电气特性和RS-232大不一样。用缆线两端的电压差值
来表示传递信号。RS485仅仅规定了接受端和发送端的电气特性。它没有规定或推荐任何数据
协议。
RS485的特点包括:
1,接口电平低,不易损坏芯片。RS485的电气特性:逻辑“1”以两线间的电压差为+(2-6)V表示;逻辑“0”以两线间的电压差为-(2~6)V表示。接口信号电平比RS232降低了,不易损坏接口电路的芯片,且该电平与TTL电平兼容,可方便与TTL电路连接。
2,传输速率高。10米时,RS485的数据最高传输速率可达35Mbps,在1200m时,传输速度可达100Kbps.
3,
抗干扰能力强。RS485接口是采用平衡驱动器和差分接收器的组合,抗共模干扰能力增强,即抗噪声干扰性好。
4,传输距离远,支持节点多。RS485总线最长可以传输1200m左右,更远的距离则需要中继传输设备支持但这时(速率≤100Kbps)才能稳定传输,一般最大支持32个节点,如果使用特制的485芯片,可以达到128个或者256个节点,最大的可以支持到400个节点。RS485推荐使用在点对点网络中,比如:线型,总线型网络等,而不能是星型,环型网络。理想情况下RS485需要2个终端匹配电阻,其阻值要求等于传输电缆的特性阻抗(一般为1202)。没有特性阻抗的话,当所有的设备都静止或者没有能量的时候就会产生噪声,而且线移需要双端的电压差。没有终接电阻的话,会使得较快速的发送端产生多个数据信号的边缘,导致数据传输出错。485推荐的一主多从连接方式如图36.1.1所示:
在这里插入图片描述
在上面的连接中,如果需要添加匹配电阻,我们一般在总线的起止端加入,也就是主机和设备4上面各加一个1202的匹配电阻。由于RS485具有传输距离远、传输速度快、支持节点多和抗干扰能力更强等特点,所以RS485有很广泛的应用。实际多设备时收发器有范围为-7V到+12V的共模电压,为了稳定传输,也有使用3线的布线方式,即在原有的A、B两线上多增加一条地线。(4线制使用全双工通讯方式,这种也叫RS422,由于布线的难度和通讯局限,相对使用得比较少)。TP8485E/SP3485可作为RS485的收发器,该芯片支持3.3V~5.5V供电,最大传输速度可达250Kbps,支持多达256个节点(单位负载为1/8的条件下),并且支持输出短路保护。该芯片的框图如图36.1.2所示:
在这里插入图片描述
图中
A、 B总线接口,用于连接 485总线。 RO是接收输出端, DI是发送数据收入端, RE是接收使能信号(低电平有效), DE是发送使能信号(高电平有效)。

电平标准

RS485 通信采用差分信号传输,通常情况下只需要两根信号线就可以进行正常的通信。
在差分信号中,逻辑0和逻辑1是用两根信号线(A+和B-)的电压差来表示。

逻辑 1:两根信号线(A+和B-)的电压差在 +2V~+6V 之间。
逻辑 0:两根信号线(A+和B-)的电压差在 -2V~-6V 之间。

1.2、硬件准备

本次实验采用的是STM32F103ZET6芯片
RS484电路为MAX485,具体电路如图所示:
在这里插入图片描述

1.3、实验

实验原理:

485通讯实质上就是软件层的串口通讯,再加上物理层上的485芯片,将TTL信号转化为查分信号进行传输,对待上就按照串口通讯就行。
编程思想:
DE: 1 发送使能;0发送禁止
RE: 0 接收使能;1接收禁止

通过1#单片机的串口3将数据发送出去,2#单片机进行接受数据,然后通过2#单片机串口1的打印出接收到的数据,

通过2#单片机的串口3将数据发送出去,1#单片机进行接受数据,然后通过1#单片机串口1的打印出接收到的数据

由于是通过485协议发送数据,每次发送前要对485传输方式设置为发送模式,完成后要改为接收模式,由于是半双工,发送完要有一定的延时,确保数据不会丢失;

具体电平转化过程为:
TTL 信号->485信号->485信号0->TTL 信号;

485双机通讯接线

在这里插入图片描述

二、 STM32cubeMX配置篇

在这里插入图片描述
画的板子外部高速晶振有问题,所以采用内部高速晶振
在这里插入图片描述
485通讯的方向选择PD7引脚初始化
在这里插入图片描述

在这里插入图片描述
串口1和3一样,选择异步就可以,传输速率115200,选择中断传输;

在这里插入图片描述
剩下的就按流程生成就行

三、代码篇

test_rs485.c
先初始化为接收模式

/**
 * @description: 初始化RS485为接受模式
 * @return {*}
 */
void Rs485_Init(void)
{
    //使能串口接收中断
    HAL_UART_Receive_IT(&huart3, rx_data, 4);
    Rs485_RecMode();
}

发送数据

/**
 * @description: 控制rs485发送数据
 * @param {uint8_t} *data 要发送的数据
 * @param {size_t} len  要发送数据的长度
 * @return {*}   0 :发送成功;-1:发送失败;
 */
int Rs485_SendData(uint8_t *data, size_t len)
{
     HAL_StatusTypeDef status;
     Rs485_SendMode();
     status = HAL_UART_Transmit(&huart3, data, len, 0xffff);
     HAL_Delay(1);
     Rs485_RecMode();
     return status == HAL_OK ? 0 : -1;
}

发送完成的回调函数,

void HAL_UART_RxCpltCallback(UART_HandleTypeDef *huart)
{
    if (huart -> Instance == USART3)
    {
        //将接收到的数据打印出来
        printf("rx_data[0] = 0x%02x\r\n", rx_data[0]);
        printf("rx_data[1] = 0x%02x\r\n", rx_data[1]);
        printf("rx_data[2] = 0x%02x\r\n", rx_data[2]);
        printf("rx_data[3] = 0x%02x\r\n", rx_data[3]);
        
        memset(rx_data, 0, 8);//记得添加头文件string.h
        //重新使能串口接收中断
        HAL_UART_Receive_IT(&huart3, rx_data, 4);

    }
    
}

main.c

串口重定向,记得在main.h中添加头文件stdio.h

/* USER CODE BEGIN 4 */
int fputc(int ch, FILE *P)
{
 HAL_UART_Transmit(&huart1, (uint8_t *)&ch, 1, 1000);
 return ch;

}
/* USER CODE END 4 */

添加要发送的数组

  /* USER CODE BEGIN 1 */
 uint8_t data_1[4] = {0x01, 0x02, 0x03, 0x04};
 uint8_t data_2[4] = {0x05, 0x06, 0x07, 0x08};
  /* USER CODE END 1 */

初始化发送,这里为了方便观察,当给1#下载程序是用TEST1,当给2#下载时,用test2

  /* USER CODE BEGIN 2 */
  // printf("STM32F103ZET6_Test 1#!\r\n");
  
  printf("STM32F103ZET6_Test 2#!\r\n");
  Rs485_Init();
  /* USER CODE END 2 */
  while (1)
  {
    // Rs485_SendData(data_1, 4);

    Rs485_SendData(data_2, 4);
  
    HAL_Delay(1000);
    /* USER CODE END WHILE */

    /* USER CODE BEGIN 3 */
  }
  /* USER CODE END 3 */
}

实验现象就是,1#单片机发送数据data_1[]到2#,2#接收到data_1[]中的数据
在这里插入图片描述
2#单片机发送数据data_2[]到2#,1#接收到data_2[]中的数据。
在这里插入图片描述

引用:STM32CubeMX | 37 - 使用RS485总线进行双板通信(SP3485)

  • 18
    点赞
  • 123
    收藏
    觉得还不错? 一键收藏
  • 7
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论 7
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值