OpenEdv-开源电子网

 找回密码
 立即注册
正点原子全套STM32/Linux/FPGA开发资料,上千讲STM32视频教程免费下载...
查看: 2659|回复: 2

大神 我写了一个modbus收发 报文 现在要发两条报文 然后交替收发 不知道怎么实现交替

[复制链接]

5

主题

6

帖子

0

精华

新手上路

积分
48
金钱
48
注册时间
2015-11-7
在线时间
0 小时
发表于 2015-11-7 09:11:30 | 显示全部楼层 |阅读模式
5金钱
#include "stm32f10x.h"
#include "stm32f10x_gpio.h"
#include "stm32f10x_tim.h"
#include "stm32f10x_usart.h"
#include "delay.h"
#include "crc.h"
u8 counter;
u8 recvBuff[256]={0};
void UART2Write(u8* data,int len);
void UART2_SendByte(u8 Data);
void USART_config(u32 bound)
{
 GPIO_InitTypeDef GPIO_InitStructure; 
 USART_InitTypeDef USART_InitStructure;
 NVIC_InitTypeDef NVIC_InitStructure;
//RCC_APB1PeriphClockCmd(RCC_APB1Periph_USART2|RCC_APB2Periph_GPIOA,ENABLE);
RCC_APB2PeriphClockCmd(RCC_APB2Periph_GPIOA | RCC_APB2Periph_AFIO,ENABLE); //这里一定要配置复用 AFIO
RCC_APB1PeriphClockCmd(RCC_APB1Periph_USART2 ,ENABLE);
USART_DeInit(USART2);
GPIO_InitStructure.GPIO_Pin = GPIO_Pin_2;
GPIO_InitStructure.GPIO_Mode =GPIO_Mode_AF_PP;    
GPIO_InitStructure.GPIO_Speed = GPIO_Speed_50MHz;
GPIO_Init(GPIOA, &GPIO_InitStructure);
GPIO_InitStructure.GPIO_Pin = GPIO_Pin_3;
GPIO_InitStructure.GPIO_Mode =GPIO_Mode_IN_FLOATING;    
GPIO_Init(GPIOA, &GPIO_InitStructure);
USART_InitStructure.USART_BaudRate = bound;
USART_InitStructure.USART_WordLength = USART_WordLength_8b;  //字长为8位数据格式
USART_InitStructure.USART_StopBits = USART_StopBits_1;   // 一个停止位
USART_InitStructure.USART_Parity = USART_Parity_No; //无奇偶校验位  
USART_InitStructure.USART_HardwareFlowControl = USART_HardwareFlowControl_None;  //为硬盘数据流控制
USART_InitStructure.USART_Mode = USART_Mode_Rx | USART_Mode_Tx; //接收发送模式
NVIC_InitStructure.NVIC_IRQChannel  = USART2_IRQn;
NVIC_InitStructure.NVIC_IRQChannelPreemptionPriority=3; 
NVIC_InitStructure.NVIC_IRQChannelSubPriority = 3;
NVIC_InitStructure.NVIC_IRQChannelCmd = ENABLE;
NVIC_Init(&NVIC_InitStructure);
USART_ITConfig(USART2, USART_IT_RXNE, ENABLE);
USART_Init(USART2, &USART_InitStructure);
USART_Cmd(USART2, ENABLE); 
}
void Timer_Config(void)
{
 TIM_TimeBaseInitTypeDef  TIM_TimeBaseStructure;
RCC_APB1PeriphClockCmd(RCC_APB1Periph_TIM3,ENABLE);//Timer3_Clock=APB1*2;
    TIM_DeInit(TIM3);                          //复位定时器
    TIM_TimeBaseStructure.TIM_Period=4999;        //定时器初始值
    TIM_TimeBaseStructure.TIM_Prescaler=(7200-1);        //时钟预分频
    TIM_TimeBaseStructure.TIM_ClockDivision=TIM_CKD_DIV1;   // 时钟分割
    TIM_TimeBaseStructure.TIM_CounterMode=TIM_CounterMode_Up; //向上计数模式
    TIM_TimeBaseInit(TIM3,&TIM_TimeBaseStructure);      //初始化定时器的值
    TIM_ClearFlag(TIM3,TIM_FLAG_Update);                //清除定时器中断标志 
    TIM_ITConfig(TIM3,TIM_IT_Update,ENABLE);        //使能中断
    TIM_Cmd(TIM3,ENABLE);                        //开启时钟
}
void NVIC_Config(void)
{
  NVIC_InitTypeDef NVIC_InitStructure;
  NVIC_PriorityGroupConfig(NVIC_PriorityGroup_1);
  NVIC_InitStructure.NVIC_IRQChannel = TIM3_IRQn;
  NVIC_InitStructure.NVIC_IRQChannelPreemptionPriority = 0;
  NVIC_InitStructure.NVIC_IRQChannelSubPriority = 0;
  NVIC_InitStructure.NVIC_IRQChannelCmd = ENABLE;
  NVIC_Init(&NVIC_InitStructure);
}
void TIM3_IRQHandler(void)//定时器中断函数
{

if (TIM_GetITStatus(TIM3, TIM_IT_Update) != RESET) // 跟下面一句连在一起用的 判断是否中断有触发,出发后就清除
{   
TIM_ClearITPendingBit(TIM3, TIM_IT_Update); //清除中断标志
counter++;

}
}
/*串口中断函数  什么时候用的到的呢 就是说main函数里面一直在执行自己的东西 然后突然有东西给单片机啦 下面判断if()发送寄存器空 被触发  就暂停工作 执行中断函数*/
void USART2_IRQHandler(void)
{
  u8 RX_dat;  
  if(USART_GetITStatus(USART2,USART_IT_RXNE)!=RESET)  //判断发生接收中断
   {
RX_dat = USART_ReceiveData(USART2);
   }
}
int main(void)
{  
int len = 0;
Timer_Config();
NVIC_Config();
SystemInit();
USART_config(9600);
delay_init(72);
while(1)
{
u16 crc;
    recvBuff[0] = 0x01; 
recvBuff[1] = 0x03;
   recvBuff[2] = 0x00;
recvBuff[3] = 0x02;
recvBuff[4] = 0x00;
recvBuff[5] = 0x08;
crc=CRC16(recvBuff,6) ; // 校验前面的数字CRC的计算函数
recvBuff[6] = (crc>>8); // 计算出的高八位给第六位
recvBuff[7] = (u8)crc; //计算出的第八位给第七位
len =8 ;
      UART2Write(recvBuff,len);
 delay_ms(50);

    }

}

/* 下面是一个发送数组的函数 首先先传递 第二个函数 是一个字节一个字节的发送*/
void UART2Write(u8* data,int len)  
{
   u8 i;
   for(i =0;i<8;i++)
{
UART2_SendByte(data);
   }
}
 void UART2_SendByte(u8 Data)  //把上面收到的字节一个一个的发送出去 

   while (!(USART2->SR & USART_FLAG_TXE)); //usart2->SR是串口状态寄存器 USART_FLAG_TXE传输数据寄存器空标记   
   USART_SendData(USART2, Data); 
}

正点原子逻辑分析仪DL16劲爆上市
回复

使用道具 举报

530

主题

11万

帖子

34

精华

管理员

Rank: 12Rank: 12Rank: 12

积分
165536
金钱
165536
注册时间
2010-12-1
在线时间
2117 小时
发表于 2015-11-7 09:11:31 | 显示全部楼层
回复

使用道具 举报

0

主题

9

帖子

0

精华

新手上路

积分
41
金钱
41
注册时间
2017-11-16
在线时间
6 小时
发表于 2017-11-18 22:10:51 | 显示全部楼层
不错,帮顶!
回复

使用道具 举报

您需要登录后才可以回帖 登录 | 立即注册

本版积分规则



关闭

原子哥极力推荐上一条 /2 下一条

正点原子公众号

QQ|手机版|OpenEdv-开源电子网 ( 粤ICP备12000418号-1 )

GMT+8, 2025-6-9 01:32

Powered by OpenEdv-开源电子网

© 2001-2030 OpenEdv-开源电子网

快速回复 返回顶部 返回列表