串口 订阅
串行接口简称串口,也称串行通信接口或串行通讯接口(通常指COM接口),是采用串行通信方式的扩展接口。串行接口 (Serial Interface)是指数据一位一位地顺序传送。其特点是通信线路简单,只要一对传输线就可以实现双向通信(可以直接利用电话线作为传输线),从而大大降低了成本,特别适用于远距离通信,但传送速度较慢。 展开全文
串行接口简称串口,也称串行通信接口或串行通讯接口(通常指COM接口),是采用串行通信方式的扩展接口。串行接口 (Serial Interface)是指数据一位一位地顺序传送。其特点是通信线路简单,只要一对传输线就可以实现双向通信(可以直接利用电话线作为传输线),从而大大降低了成本,特别适用于远距离通信,但传送速度较慢。
信息
别    称
通常指COM接口
简    称
串口
中文名
串行接口
外文名
Serial Interface
串行接口定义
串行接口 (Serial Interface) 是指数据一位一位地顺序传送,其特点是通信线路简单,只要一对传输线就可以实现双向通信(可以直接利用电话线作为传输线),从而大大降低了成本,特别适用于远距离通信,但传送速度较慢。一条信息的各位数据被逐位按顺序传送的通讯方式称为串行通讯。串行通讯的特点是:数据位的传送,按位顺序进行,最少只需一根传输线即可完成;成本低但传送速度慢。串行通讯的距离可以从几米到几千米;根据信息的传送方向,串行通讯可以进一步分为单工、半双工和全双工三种。
收起全文
精华内容
下载资源
问答
  • Arduino - 串口操作函数与示例代码大全

    万次阅读 多人点赞 2015-12-16 22:36:02
    本文总结了Arduino常用串口操作函数的说明、语法、参数、返回值。根据函数定义编写了示例代码,并通过实验解释了每个函数的具体用法。是对Arduino串口操作函数的较全面总结,可作为工具贴查找使用。

     

    Arduino - 串口操作函数与示例代码大全

     

    本文总结了Arduino常用串口操作函数,函数说明部分来源于Arduino 官网串口使用指南,示例与实验部分为自编。本文是对Arduino串口操作函数的较全面总结,可作为工具贴查找使用。

    1.串口设置

    Serial.begin();  

    说明

     

    开启串口,通常置于setup()函数中。

    语法

    Serial.begin(speed);  

    Serial.begin(speed,config);  

    参数

    speed: 波特率,一般取值300, 1200, 2400, 4800, 9600, 14400, 19200, 28800, 38400, 57600,115200

    config: 设置数据位、校验位和停止位。例如Serial.begin(speed,Serial_8N1);  Serial_8N1中:8表示8个数据位,N表示没有校验,1表示有1个停止位。

    返回

    None

    示例

     

    void setup() { 
    Serial.begin(9600); // opensserial port, sets data rate to 9600 bps 
    }

     

    Serial.end(); 

    说明

    禁止串口传输函数。此时串口传输的pin脚可以作为数字IO脚使用。

    语法 

    Serial.end()

    参数

    None

    返回 

    None

    2.清空串口缓存

    Serial.flush();   

    说明

    1.0版本之前为清空串口缓存,现在该函数作用为等待输出数据传送完毕。如果要清空串口缓存的话,可以使用:while(Serial.read() >= 0)来代替。

    语法 

    Serial.flush ()

    参数

    None

    返回 

    None

    while(Serial.read()>= 0){}

    说明

    因Serial.read()函数读取串口缓存中的一个字符,并删除已读字符。因此可以用这句代码来清空串口缓存。实验代码详见下文代码。

    语法 

    while(Serial.read() >=0){}

    参数

    None

    返回 

    None

    3.输出串口数据

    将打印输出串口数据的函数在这一小节给出,方便大家阅读后面的各个示例代码。

    Serial.print(); 

    说明

    串口输出数据函数,写入字符串数据到串口。

    语法

    Serial.print(val)

    Serial.print(val,format)

    参数

    val: 打印的值,任意数据类型

    format: 输出的数据格式,包括整数类型和浮点型数据的小数点位数。

    示例

     

    • Serial.print(78, BIN) 得到 "1001110"
    • Serial.print(78, OCT) 得到 "116"
    • Serial.print(78, DEC) 得到 "78"
    • Serial.print(78, HEX) 得到 "4E"
    • Serial.print(1.23456, 0) 得到 "1"
    • Serial.print(1.23456, 2) 得到 "1.23"
    • Serial.print(1.23456, 4) 得到 "1.2346"
    • Serial.print('N') 得到 "N"
    • Serial.print("Hello world.") 得到 "Hello world."

    Serial.println();

    说明

    写入字符串数据,并换行。实验代码详见下文。

    语法

    Serial.println(val) 
    Serial.println(val,format)

     

    参数

     

    val: 打印的值,任意数据类型 
    format: 输出的数据格式,包括整数类型和浮点型数据的小数点位数。

    返回 

    字节

    Serial.SerialEvent();

    串口数据准备好时触发的事件函数,即串口数据准备好调用该函数。

    语法 

    Serial.serialEvent{//statements}

    参数 

    statements: 任何有效的语句。

    4.读串口缓存区数据

    Serial.available();

    说明

    判断串口缓冲器的状态函数,用以判断数据是否送达串口。注意使用时通常用delay(100)以保证串口字符接收完毕,即保证Serial.available()返回的是缓冲区准确的可读字节数。

    语法

    Serial.available();

    参数

    None

    返回

    返回缓冲区可读字节数目

    示例

     

    void setup() {
      Serial.begin(9600);
      while(Serial.read()>= 0){}//clear serialbuffer
    }
     
    void loop() {
       if (Serial.available() > 0) {
        delay(100); // 等待数据传完
        int numdata = Serial.available();
        Serial.print("Serial.available = :");
        Serial.println(numdata);
      }
      while(Serial.read()>=0){} //清空串口缓存
    }

    实验结果

     

    Serial.read();

    说明

    读取串口数据,一次读一个字符,读完后删除已读数据。

    语法

    Serial.read();

    参数

    None

    返回

    返回串口缓存中第一个可读字节,当没有可读数据时返回-1,整数类型。

    示例

     

    char comchar;
     
    void setup() {
      Serial.begin(9600);
      while(Serial.read()>= 0){}/ /clear serialbuffer
    }
     
    void loop() {
      // read data from serial port
     
      while(Serial.available()>0){
        comchar = Serial.read();//读串口第一个字节
        Serial.print("Serial.read: ");
        Serial.println(comchar);
        delay(100); 
        }
     }

     

    实验结果

    从实验结果可以看出:Serial.read()每次从串口缓存中读取第一个字符,并将读过的字符删除。

     

    Serial.peek(); 

    说明

    读串口缓存中下一字节的数据(字符型),但不从内部缓存中删除该数据。也就是说,连续的调用peek()将返回同一个字符。而调用read()则会返回下一个字符。

    语法

    Serial.peek();

    参数

    None

    返回

    返回串口缓存中下一字节(字符)的数据,如果没有返回-1,整数int型

    示例

     

    char comchar;
     
    void setup() {
      Serial.begin(9600);
      while(Serial.read()>= 0){}//clear serialbuffer
    }
     
    void loop() {
      // read data from serial port
     
      while(Serial.available()>0){
        comchar = Serial.peek();
        Serial.print("Serial.peek: ");
        Serial.println(comchar);
        delay(100); 
        }
     }

     

    实验结果

     

    从实验结果可以看出:Serial.peek()每次从串口缓存中读取一个字符,并不会将读过的字符删除。第二次读取时仍然为同一个字符。

     

    Serial.readBytes(buffer,length);

    说明

    从串口读取指定长度length的字符到缓存数组buffer。

    语法

    Serial.readBytes(buffer,length);

    参数

    buffer: 缓存变量

    length:设定的读取长度

    返回

    返回存入缓存的字符数,0表示没有有效数据。

    示例

     

    char buffer[18];
    int numdata=0;
     
    void setup() {
      Serial.begin(9600);
      while(Serial.read()>= 0){}//clear serial port
    }
     
    void loop() {
      // read data from serial port
      if(Serial.available()>0){
          delay(100);
          numdata = Serial.readBytes(buffer,3);
          Serial.print("Serial.readBytes:");
          Serial.println(buffer);    
        }
        // clear serial buffer
      while(Serial.read() >= 0){}
      for(int i=0; i<18; i++){
            buffer[i]='\0';
        }
    }

    实验结果

     
    从串口缓存读取指定长度为3的字节。

     

    Serial.readBytesUntil(character,buffer,length);

    说明

    从串口缓存读取指定长度的字符到数组buffer,遇到终止字符character后停止。

    语法

    Serial.readBytesUntil(character ,buffer,length);

    参数

    character : 查找的字符 (char)

    buffer: 存储读取数据的缓存(char[] 或byte[])

    length:设定的读取长度

    返回

    返回存入缓存的字符数,0表示没有有效数据。

    示例

     

    char buffer[18];
    char character = ','; //终止字符
    int numdata=0;
     
    void setup() {
      Serial.begin(9600);
      while(Serial.read()>= 0){}//clear serialport
    }
     
    void loop() {
      // read data from serial port
      if(Serial.available()>0){
          delay(100);
          numdata =Serial.readBytesUntil(character,buffer,3);
          Serial.print("Serial.readBytes:");
          Serial.println(buffer);    
        }
        // clear serial buffer
      while(Serial.read() >= 0){}
      for(int i=0; i<18; i++){
            buffer[i]='\0';
        }
    }

     

    实验结果

     

    从串口缓存中读取3个字符,当遇到","时终止读取。

    Serial.readString();

    说明

    从串口缓存区读取全部数据到一个字符串型变量。

    语法

    Serial.readString();

    参数

    None

    返回

    返回从串口缓存区中读取的一个字符串。

    示例

     

    String comdata = "";
     
    void setup() {
      Serial.begin(9600);
      while(Serial.read()>= 0){} //clear serialbuffer
    }
     
    void loop() {
      // read data from serial port
      if(Serial.available()>0){
          delay(100);
          comdata = Serial.readString();
          Serial.print("Serial.readString:");
          Serial.println(comdata);
        }
        comdata = "";
    }

    实验结果

     

    从实验结果可以看出:Serial.readString()从串口缓存中读取字符至字符串。

     

     

    Serial.readStringUntil();

    说明

    从串口缓存区读取字符到一个字符串型变量,直至读完或遇到某终止字符。

    语法

    Serial.readStringUntil(terminator)

    参数

    terminator:终止字符(cha型)

    返回

    从串口缓存区中读取的整个字符串,直至检测到终止字符。

    示例

     

    String comdata = "";
    char terminator = ',';
    void setup() {
      Serial.begin(9600);
      while(Serial.read()>= 0){} //clear serialbuffer
    }
     
    void loop() {
      // read data from serial port
      if(Serial.available()>0){
          delay(100);
          comdata =Serial.readStringUntil(terminator);
         Serial.print("Serial.readStringUntil: ");
          Serial.println(comdata);
        }
        while(Serial.read()>= 0){}
    }

     

    实验结果

     

     

     

    从串口读取所有字符存放于字符串comdata,直至遇到字符","时终止读取。

    Serial.parseFloat();

    说明

    读串口缓存区第一个有效的浮点型数据,数字将被跳过。当读到第一个非浮点数时函数结束。

    语法

    Serial.parseFloat()

    参数

    None

    返回

    返回串口缓存区第一个有效的浮点型数据,数字将被跳过。

    示例

     

    float comfloat;
     
    void setup() {
      Serial.begin(9600);
      while(Serial.read()>= 0){}//clear serialbuffer
    }
     
    void loop() {
      // read data from serial port
      if(Serial.available()>0){
          delay(100);
          comfloat = Serial.parseFloat();
          Serial.print("Serial.parseFloat:");
          Serial.println(comfloat);
        }
        // clear serial buffer
        while(Serial.read() >= 0){}
    }

    实验结果

     

    从实验结果可以看出:Serial. parseFloat()从串口缓存中读取第一个有效的浮点数,第一个有效数字之前的负号也将被读取,独立的负号将被舍弃。

    Serial.parseInt()

    说明

    从串口接收数据流中读取第一个有效整数(包括负数)。

    注意:

     

    • 非数字的首字符或者负号将被跳过
    • 当可配置的超时值没有读到有效字符时,或者读不到有效整数时,分析停止
    • 如果超时且读不到有效整数时,返回0

     

    语法

    Serial.parseInt()

    Serial.parseInt(charskipChar)

    参数

    skipChar用于在搜索中跳过指定字符(此用法未知)

    返回

    返回下一个有效整型值。

    示例

     

    int comInt;
     
    voidsetup() {
      Serial.begin(9600);
      while(Serial.read()>= 0){}//clear serialbuffer
    }
     
    void loop() {
      // read data from serial port
      if(Serial.available()>0){
          delay(100);
          comInt = Serial.parseInt();
          Serial.print("Serial.parseInt:");
          Serial.println(comInt);
        }
        // clear serial buffer
        while(Serial.read() >= 0){}
    }

    实验结果

     

    从实验结果可以看出:Serial. parseInt()从串口缓存中读取第一个有效整数,第一个有效数字之前的负号也将被读取,独立的负号将被舍弃。

     

     

    5.串口查找指定字符串

    Serial.find()

    说明

    从串口缓存区读取数据,寻找目标字符串target(char型)

    语法

    char target[] = ”目标字符串”;

    Serial.find(target); 

    参数

    target: 目标字符串(char型)

    返回

    找到目标字符串返回真,否则为假

    示例

     

    char target[] ="test";
     
    void setup() {
      Serial.begin(9600);
      while(Serial.read()>= 0){}//clear serialbuffer
    }
     
    void loop() {
      // read data from serial port
       if(Serial.available()>0){
          delay(100);
          if( Serial.find(target)){
             Serial.print("find traget:");
             Serial.println(target);       
            }
         }
        // clear serial buffer
        while(Serial.read() >= 0){}
    }

    实验结果

     


    串口输入字符中只要有test,函数返回真,打印出目标字符串”test”,否则返回假,不打印任何值。

    Serial.findUntil(target,terminal);  

    说明

    从串口缓存区读取数据,寻找目标字符串target(char型数组),直到出现给定字符串terminal(char型),找到为真,否则为假。

    语法

    Serial.findUntil(target,terminal); 

    参数

    target : 目标字符串(char型)

    terminal : 结束搜索字符串(char型)

    返回

    如果在找到终止字符terminal之前找到目标字符target,返回真,否则返回假。

    示例

     

    char target[] ="test";
    char terminal[] ="end";
     
    void setup() {
      Serial.begin(9600);
      while(Serial.read()>= 0){}//clear serialbuffer
    }
     
    void loop() {
      // read data from serial port
       if(Serial.available()>0){
          delay(100);
          if( Serial.findUntil(target,terminal)){
             Serial.print("find traget:");
             Serial.println(target);
            }
         }
        // clear serial buffer
        while(Serial.read() >= 0){}
    }

    实验结果

     

    如果串口缓存中有目标字符”test”,返回真,但如果先遇到终止字符串”end”则函数立即终止,不论字符串后面有没有目标字符”test”。

    6.向串口写数据

    Serial.write();    

    说明

    串口输出数据函数。写二进制数据到串口。

    语法 

    Serial.write(val) 
    Serial.write(str) 
    Serial.write(buf, len)

    参数 

    val: 字节 
    str: 一串字节 
    buf: 字节数组 
    len: buf的长度

    返回 

    字节长度

    示例

     

    void setup(){ 
    Serial.begin(9600); 
    }
    void loop(){ 
      Serial.write(45); // send a byte with thevalue 45 
      int bytesSent = Serial.write(“hello”); //sendthe string “hello” and return the length of the string. 
    }

    转载请注明:http://blog.csdn.net/iracer/article/details/50334041


    新书终于面市啦,《机器学习原理与编程实战》连接原理与实战,感兴趣的同学请移步:

    https://blog.csdn.net/iracer/article/details/116051674?spm=1001.2014.3001.5501

    展开全文
  • 【STM32】HAL库 STM32CubeMX教程四---UART串口通信详解

    万次阅读 多人点赞 2019-08-11 08:57:51
    今天我们学习STM32CubeMX串口的操作,以及HAL库串口的配置,我们会详细的讲解各个模块的使用和具体功能,并且基于HAL库实现Printf函数功能重定向,UART中断接收,本系列教程将HAL库与STM32CubeMX结合在一起讲解,使...

    前言: 

    今天我们学习STM32CubeMX串口的操作,以及HAL库串口的配置,我们会详细的讲解各个模块的使用和具体功能,并且基于HAL库实现Printf函数功能重定向,UART中断接收,本系列教程将HAL库与STM32CubeMX结合在一起讲解,使您可以更快速的学会各个模块的使用

     

    所用工具

    1、芯片: STM32F407ZET6

    2、STM32CubeMx软件

    3、IDE: MDK-Keil软件

    4、STM32F1xx/STM32F4xxHAL库 

    5、串口: 使用USART1 PA9,PA10

    知识概括:

    通过本篇博客您将学到:

    STM32CubeMX创建串口例程

    HAL库UATR函数库

    重定义printf函数

    HAL库,UART中断接收

    HAL库UATR接收与发送例程

    工程创建

     

    1设置RCC

    • 设置高速外部时钟HSE 选择外部时钟源

    2设置串口

    • 1点击USATR1   
    • 2设置MODE为异步通信(Asynchronous)       
    • 3基础参数:波特率为115200 Bits/s。传输数据长度为8 Bit。奇偶检验无,停止位1      接收和发送都使能 
    • 4GPIO引脚设置 USART1_RX/USART_TX
    • 5 NVIC Settings 一栏使能接收中断

    3设置时钟

    我的是  外部晶振为8MHz 

    • 1选择外部时钟HSE 8MHz   
    • 2PLL锁相环倍频72倍
    • 3系统时钟来源选择为PLL
    • 4设置APB1分频器为 /2

    32的时钟树框图  如果不懂的话请看《【STM32】系统时钟RCC详解(超详细,超全面)》

     

    4项目文件设置

    • 1 设置项目名称
    • 2 设置存储路径
    • 3 选择所用IDE

    5创建工程文件

    然后点击GENERATE CODE  创建工程

    配置下载工具

    新建的工程所有配置都是默认的  我们需要自行选择下载模式,勾选上下载后复位运行

    HAL库UART函数库介绍

     

      UART结构体定义

    UART_HandleTypeDef huart1;

    UART的名称定义,这个结构体中存放了UART所有用到的功能,后面的别名就是我们所用的uart串口的别名,默认为huart1

    可以自行修改

    1、串口发送/接收函数

    • HAL_UART_Transmit();串口发送数据,使用超时管理机制 
    • HAL_UART_Receive();串口接收数据,使用超时管理机制
    • HAL_UART_Transmit_IT();串口中断模式发送  
    • HAL_UART_Receive_IT();串口中断模式接收
    • HAL_UART_Transmit_DMA();串口DMA模式发送
    • HAL_UART_Transmit_DMA();串口DMA模式接收

    这几个函数的参数基本都是一样的,我们挑两个讲解一下

    串口发送数据:

    HAL_UART_Transmit(UART_HandleTypeDef *huart, uint8_t *pData, uint16_t Size, uint32_t Timeout)

    功能:串口发送指定长度的数据。如果超时没发送完成,则不再发送,返回超时标志(HAL_TIMEOUT)。

    参数:

    • UART_HandleTypeDef *huart      UATR的别名    如 :   UART_HandleTypeDef huart1;   别名就是huart1  
    • *pData      需要发送的数据 
    • Size    发送的字节数
    • Timeout   最大发送时间,发送数据超过该时间退出发送   
    举例:   HAL_UART_Transmit(&huart1, (uint8_t *)ZZX, 3, 0xffff);   //串口发送三个字节数据,最大传输时间0xffff

    中断接收数据:

    HAL_UART_Receive_IT(UART_HandleTypeDef *huart, uint8_t *pData, uint16_t Size)

    功能:串口中断接收,以中断方式接收指定长度数据。
    大致过程是,设置数据存放位置,接收数据长度,然后使能串口接收中断。接收到数据时,会触发串口中断。
    再然后,串口中断函数处理,直到接收到指定长度数据,而后关闭中断,进入中断接收回调函数,不再触发接收中断。(只触发一次中断)

    参数:

    • UART_HandleTypeDef *huart      UATR的别名    如 :   UART_HandleTypeDef huart1;   别名就是huart1  
    • *pData      接收到的数据存放地址
    • Size    接收的字节数
    举例:    HAL_UART_Receive_IT(&huart1,(uint8_t *)&value,1);   //中断接收一个字符,存储到value中

    2、串口中断函数

     

    • HAL_UART_IRQHandler(UART_HandleTypeDef *huart);  //串口中断处理函数
    • HAL_UART_TxCpltCallback(UART_HandleTypeDef *huart);  //串口发送中断回调函数
    • HAL_UART_TxHalfCpltCallback(UART_HandleTypeDef *huart);  //串口发送一半中断回调函数(用的较少)
    • HAL_UART_RxCpltCallback(UART_HandleTypeDef *huart);  //串口接收中断回调函数
    • HAL_UART_RxHalfCpltCallback(UART_HandleTypeDef *huart);//串口接收一半回调函数(用的较少)
    • HAL_UART_ErrorCallback();串口接收错误函数

    串口接收中断回调函数:

    HAL_UART_RxCpltCallback(UART_HandleTypeDef *huart);  

    功能:HAL库的中断进行完之后,并不会直接退出,而是会进入中断回调函数中,用户可以在其中设置代码,

               串口中断接收完成之后,会进入该函数,该函数为空函数,用户需自行修改,

    参数:

    • UART_HandleTypeDef *huart      UATR的别名    如 :   UART_HandleTypeDef huart1;   别名就是huart1  
    举例:   HAL_UART_RxCpltCallback(&huart1){           //用户设定的代码               }

    串口中断处理函数

    HAL_UART_IRQHandler(UART_HandleTypeDef *huart);  

    功能:对接收到的数据进行判断和处理  判断是发送中断还是接收中断,然后进行数据的发送和接收,在中断服务函数中使用

     

    如果接收数据,则会进行接收中断处理函数

     /* UART in mode Receiver ---------------------------------------------------*/
      if((tmp_flag != RESET) && (tmp_it_source != RESET))
      { 
        UART_Receive_IT(huart);
      }
    

    如果发送数据,则会进行发送中断处理函数

      /* UART in mode Transmitter ------------------------------------------------*/
      if (((isrflags & USART_SR_TXE) != RESET) && ((cr1its & USART_CR1_TXEIE) != RESET))
      {
        UART_Transmit_IT(huart);
        return;
      }

    3串口查询函数

      HAL_UART_GetState();  判断UART的接收是否结束,或者发送数据是否忙碌

      举例:     

    while(HAL_UART_GetState(&huart4) == HAL_UART_STATE_BUSY_TX)   //检测UART发送结束

     

    USART接收与发送

     

    重新定义printf函数

    • 在 stm32f4xx_hal.c中包含#include <stdio.h>
    #include "stm32f4xx_hal.h"
    #include <stdio.h>
    extern UART_HandleTypeDef huart1;   //声明串口
    • 在 stm32f4xx_hal.c 中重写fget和fput函数
    • /**
        * 函数功能: 重定向c库函数printf到DEBUG_USARTx
        * 输入参数: 无
        * 返 回 值: 无
        * 说    明:无
        */
      int fputc(int ch, FILE *f)
      {
        HAL_UART_Transmit(&huart1, (uint8_t *)&ch, 1, 0xffff);
        return ch;
      }
      
      /**
        * 函数功能: 重定向c库函数getchar,scanf到DEBUG_USARTx
        * 输入参数: 无
        * 返 回 值: 无
        * 说    明:无
        */
      int fgetc(FILE *f)
      {
        uint8_t ch = 0;
        HAL_UART_Receive(&huart1, &ch, 1, 0xffff);
        return ch;
      }
      
      在main.c中添加
     #define RXBUFFERSIZE  256
    char RxBuffer[RXBUFFERSIZE]; 
    
      while (1)
      {
        /* USER CODE END WHILE */
    			printf("Z小旋测试\n");
    			HAL_Delay(1000);
        /* USER CODE BEGIN 3 */
      }

    之后便可以使用Printf函数和Scanf,getchar函数

    UART接收中断

    因为中断接收函数只能触发一次接收中断,所以我们需要在中断回调函数中再调用一次中断接收函数

    具体流程:

    1、初始化串口

    2、在main中第一次调用接收中断函数

    3、进入接收中断,接收完数据  进入中断回调函数

    4、修改HAL_UART_RxCpltCallback中断回调函数,处理接收的数据,

    5  回调函数中要调用一次HAL_UART_Receive_IT函数,使得程序可以重新触发接收中断

    函数流程图:

    HAL_UART_Receive_IT(中断接收函数   ->  USART2_IRQHandler(void)(中断服务函数)    ->    HAL_UART_IRQHandler(UART_HandleTypeDef *huart)(中断处理函数)    ->    UART_Receive_IT(UART_HandleTypeDef *huart) (接收函数)   ->    HAL_UART_RxCpltCallback(huart);(中断回调函数)

    HAL_UART_RxCpltCallback函数就是用户要重写在main.c里的回调函数。

    代码实现:

        并在main.c中添加下列定义:

    #include <string.h>
    
    #define RXBUFFERSIZE  256     //最大接收字节数
    char RxBuffer[RXBUFFERSIZE];   //接收数据
    uint8_t aRxBuffer;			//接收中断缓冲
    uint8_t Uart1_Rx_Cnt = 0;		//接收缓冲计数
    

    在main()主函数中,调用一次接收中断函数

    /* USER CODE BEGIN 2 */
    	HAL_UART_Receive_IT(&huart1, (uint8_t *)&aRxBuffer, 1);
    /* USER CODE END 2 */
    

    在main.c下方添加中断回调函数

    /* USER CODE BEGIN 4 */
    
    void HAL_UART_RxCpltCallback(UART_HandleTypeDef *huart)
    {
      /* Prevent unused argument(s) compilation warning */
      UNUSED(huart);
      /* NOTE: This function Should not be modified, when the callback is needed,
               the HAL_UART_TxCpltCallback could be implemented in the user file
       */
     
    	if(Uart1_Rx_Cnt >= 255)  //溢出判断
    	{
    		Uart1_Rx_Cnt = 0;
    		memset(RxBuffer,0x00,sizeof(RxBuffer));
    		HAL_UART_Transmit(&huart1, (uint8_t *)"数据溢出", 10,0xFFFF); 	
            
    	}
    	else
    	{
    		RxBuffer[Uart1_Rx_Cnt++] = aRxBuffer;   //接收数据转存
    	
    		if((RxBuffer[Uart1_Rx_Cnt-1] == 0x0A)&&(RxBuffer[Uart1_Rx_Cnt-2] == 0x0D)) //判断结束位
    		{
    			HAL_UART_Transmit(&huart1, (uint8_t *)&RxBuffer, Uart1_Rx_Cnt,0xFFFF); //将收到的信息发送出去
                while(HAL_UART_GetState(&huart1) == HAL_UART_STATE_BUSY_TX);//检测UART发送结束
    			Uart1_Rx_Cnt = 0;
    			memset(RxBuffer,0x00,sizeof(RxBuffer)); //清空数组
    		}
    	}
    	
    	HAL_UART_Receive_IT(&huart1, (uint8_t *)&aRxBuffer, 1);   //再开启接收中断
    }
    /* USER CODE END 4 */
    

    发送数据被正常返回

     

     

    展开全文
  • c# 简单的串口通信 新手篇

    万次阅读 多人点赞 2018-09-26 11:17:10
    最近自己闲着 自学了C# ,本人不是搞软件的 ,搞嵌入式的 ,经常要用串口调试工具来调试 ,有时候还要处理一些数据但是市面上的不能满足我的要求 ,正好一个项目需要学习C#,借此机会来开发一个串口 ,说不定对我也...

    最近自己闲着 自学了C# ,本人不是搞软件的 ,搞嵌入式的 ,经常要用串口调试工具来调试 ,有时候还要处理一些数据但是市面上的不能满足我的要求 ,正好一个项目需要学习C#,借此机会来开发一个串口  ,说不定对我也有用!

    话不多说先看看成果!

    串口调试工具 功能:

       通过串口设置设置相应的参数  ,串口检测  检测插上的串口号 ,发送与接收数据,HEX显示 ,定时发送,文件保存。

    1.在vs2017 菜单栏点击 文件  -> 新建项目, 创建c#下的 windows窗体应用:

    在窗体上添加四个  “GroupBox”控件 ,分别将窗体分为“串口设置”,“数据接收”,“数据发送”,”文件操作“。

    添加若干个"Label”和"ComboBOX”   ,添加两个" RodioButton  " 给字符与HEX  选择,添加若干个 “Button” 

    发送与接收 添加 TextBox 控件。

    不说了上代码!

    设置一下标志位与 Form1 初始化。

    串口检测 界面初始化

    •  

      private void SetPortProperty () //  设置串口名
            {
                sp = new SerialPort();
                sp.PortName = cbxComPort.Text.Trim();                //设置串口名
                sp.BaudRate = Convert.ToInt32(cbxBaudRate.Text.Trim());  //设置串口波特率
                float f = Convert.ToSingle(cbxStopBits.Text.Trim());     //设置停止位
                if(f==0)
                {
                    sp.StopBits = StopBits.None;
                }
                else if(f==1)
                {
                    sp.StopBits = StopBits.One;
                }
                else if(f==1.5)
                {
                    sp.StopBits = StopBits.OnePointFive;
                }
                else if (f == 2)
                {
                    sp.StopBits = StopBits.Two;
                }
                else
                {
                    sp.StopBits = StopBits.One;
                }


                sp.DataBits = Convert.ToInt16(cbxDataBits.Text.Trim()); //设置数据位

                string s = cbxParity.Text.Trim();                //设置奇偶校验
                if (s.CompareTo("无") == 0)
                {
                    sp.Parity = Parity.None;
                }
                else if (s.CompareTo("奇校验") == 0)
                {
                    sp.Parity = Parity.Odd;
                }
                else if (s.CompareTo("偶校验") == 0)
                {
                    sp.Parity = Parity.Even;
                }
                else
                {
                    sp.Parity = Parity.None;
                }

                sp.ReadTimeout = -1;     //  设置超时读取时间
                sp.RtsEnable = true;

                // 定义Data Received 事件 ,  当串口收到数据后触发事件
                sp.DataReceived += new SerialDataReceivedEventHandler(sp_DataReceived);
                if (rbnHex.Checked)
                {
                    isHex = true;
                }
                else
                {
                    isHex = false;
                }

               

            }

    上面3图  发送 数据      清除数据   打开文件

    发送文件

    定时发送

    需要完整代码  私信  。

    上面代码都是自己写的如果那里有不足之处还请多多指教   ,如果觉得对你有帮助就关注一下。

    下载链接 : https://download.csdn.net/download/misslxy/12608949  解压密码私信

    展开全文
  • Android 串口编程

    千次下载 热门讨论 2011-11-28 23:28:32
    Android 串口编程,《Android 串口编程原理和实现方式》代码
  • HC-05蓝牙串口通信模块应该是使用最广泛的一种蓝牙模块之一了。为什么呢? 因为HC05模块是一款高性能主从一体蓝牙串口模块,可以不用知道太多蓝牙相关知识就可以很好的上手。说白了,只是个蓝牙转串口的设备,你...

    HC-05蓝牙串口通信模块应该是使用最广泛的一种蓝牙模块之一了。为什么呢?

    因为HC05模块是一款高性能主从一体蓝牙串口模块,可以不用知道太多蓝牙相关知识就可以很好的上手。说白了,只是个蓝牙转串口的设备,你只要知道串口怎么编程使用,就可以了,实现了所谓的透明传输。

    但是就是这么一个很常见的模块,网上很多的博客写的都是错的,或者都是很不详细的。

    所以本文就介绍一下这款蓝牙通信模块的使用,包括蓝牙模块的调试、手机与蓝牙模块之间的传输、手机蓝牙控制STM32单片机,应该是逐渐深入的一个过程。但是这仅仅是使用,以后有时间应该会对蓝牙有一个稍微深度的学习,而不能仅仅是浮于表面,只会用。

     

    模块名称:HC-05蓝牙串口通信模块

    参考资料:HC-05蓝牙串口通信模块官方资料包

    知识储备:【STM32】串口通信基本原理(超基础、详细版)

    其他模块:USB转TTL模块、手机蓝牙串口助手app

    手机蓝牙串口助手软件,可以点击链接下载:蓝牙串口。因为这是我见过所有手机端界面最好看的了,其他的界面都有点太糟糕了。

     

    蓝牙模块的调试

    准备工作

    USB转TTL模块与HC-05蓝牙模块的接线:

    两模块共地,两模块共VCC(VCC取5V);蓝牙模块的RX接转换模块的TX,蓝牙模块的TX接转换模块的RX。如下图所示:

    这个时候就要将转换模块连接到电脑上,然后利用串口调试助手进行蓝牙模块的调试。

    附可能会用到的驱动:链接:https://pan.baidu.com/s/1bpYLfCr 密码:yabv

    蓝牙模块的调试

    HC-05蓝牙串口通讯模块具有两种工作模式:命令响应工作模式和自动连接工作模式。在自动连接工作模式下模块又可分为主(Master)、从(Slave)和回环(Loopback)三种工作角色。

    • 当模块处于自动连接工作模式时,将自动根据事先设定的方式连接的数据传输;
    • 当模块处于命令响应工作模式时能执行AT命令,用户可向模块发送各种AT 指令,为模块设定控制参数或发布控制命令。

    怎么进入命令响应工作模式?

    进入命令响应工作模式有两种方法:

    • 模块上电,未配对情况下就是AT模式,波特率为模块本身的波特率,默认:9600,发送一次AT指令时需要置高一次PIO11;
    • PIO11 置高电平后,再给模块上电,此时模块进入AT 模式,波特率固定为:38400,可以直接发送AT指令。

    什么叫做置高一次PIO11?

    在蓝牙模块中有一个小按键,按一下就置高一次PIO11。也就是说,第一种方法需要每发送一次AT指令按一次;而第二种方式是长按的过程中上电,之后就无需再管了,直接发送AT命令即可。

    需要注意一下,两种进入命令响应工作模式的方式使用的波特率是不一样的,建议使用第二种方式。

    怎么区分进了命令响应工作模式呢?

    在蓝牙模块上有灯,当灯快闪的时候,就是自动连接工作模式;当灯慢闪的时候,就是命令响应工作模式。

    AT命令

    进入到命令响应工作模式之后,就可以使用串口调试助手进行蓝牙调试了。

    首先有一点,AT指令不区分大小写,均以回车、换行结尾。下面介绍常用的AT指令:

    常用AT指令
    指令名响应含义
    ATOK测试指令
    AT+RESETOK模块复位
    AT+VERSION?+VERSION:<Param> OK获得软件版本号
    AT+ORGLOK恢复默认状态
    AT+ADDR?+ADDR:<Param> OK获得蓝牙模块地址
    AT+NAME=<Param>OK设置设备名称
    AT+NAME?+NAME:<Param> OK获得设备名称
    AT+PSWD=<Param>OK设置模块密码
    AT+PSWD?+PSWD:<Param> OK获得模块密码
    AT+UART=<Param1>,<Param2>,<Param3>OK设置串口参数
    AT+UART?+UART:<Param1>,<Param2>,<Param3> OK获得串口参数

    对于AT指令,有几点注意:

    • AT+NAME?:获得设备名称,这个AT指令有很大可能性是没有返回的,因为我也看到了很多的例子……,但是其他的指令都是没有问题的,直接设置设备名称就行了;
    • AT+UART?:获得串口参数,串口的参数一共有三个,波特率、停止位、检验位。其取值如下:
    串口参数
    参数名称取值
    波特率

    2400、4800、9600、19200、38400、5760、

    115200、230400、460800、921600、1382400

    停止位

    0:1位

    1:2位

    校验位0:NONE  1:Odd  2:Even

    其默认值为:9600,0,0。

    例子:

    本文中,蓝牙串口的波特率设置成115200。之后的内容,就会采用这个波特率来进行通讯了。

     

    手机与蓝牙模块之间的传输

    直接将蓝牙模块与转换模块连接,再讲其连接到电脑上,蓝牙模块直接进入自动连接工作模式。

    此时手机打开蓝牙串口调试应用,用其来连接蓝牙模块。手机蓝牙串口助手软件,可以点击链接下载:蓝牙串口。万分推荐这款,因为界面脱离了那种黑不溜秋的感觉,比较简洁、清爽。

    这个软件的使用:点击界面右下角蓝牙的标志,选择蓝牙进行连接。

    然后在电脑上的调试助手和手机的蓝牙串口调试应用之间就可以相互传输了,比如:

    可以清楚的看到:电脑向手机发送了“hello you”,手机向电脑发送了“hello world”。

     

    手机蓝牙控制STM32单片机

    之前的两个例子都是相比较而言比较简单的,这个例子将会涉及到程序的内容了。

    实现功能:手机通过蓝牙,向STM32单片机发送消息,STM32接收到消息之后原封不动的返回给手机。当然如果掌握了这个例子,也可以修改成,手机发送特定的消息,然后,STM32单片机做出相对应的动作。比如:点亮LED等、发动电机等等。

    连接说明

    使用USART1进行试验,也就是说STM32选取PA9、PA10来和HC-05进行连接。同时手机通过蓝牙来和HC-05进行连接。

    原理就是:手机通过蓝牙传输到HC-05上,再通过串口通信和STM32通信;而之前一般都是电脑上通过USB线转串口的方式,通过串口和STM32通信。本质上没有区别的。

    这个时候就应该更加深刻地体会到了本文开篇的一句话:说白了,只是个蓝牙转串口的设备,你只要知道串口怎么编程使用,就可以了,实现了所谓的透明传输。蓝牙的相关一切都被封装起来了,都不需要接触到。

    STM32控制程序

    #include "stm32f10x.h"
    
     void My_USART1_Init(void)  
    {  
        GPIO_InitTypeDef GPIO_InitStrue;  
        USART_InitTypeDef USART_InitStrue;  
        NVIC_InitTypeDef NVIC_InitStrue;  
          
        RCC_APB2PeriphClockCmd(RCC_APB2Periph_GPIOA,ENABLE);//GPIO端口使能  
        RCC_APB2PeriphClockCmd(RCC_APB2Periph_USART1,ENABLE);//串口端口使能  
          
        GPIO_InitStrue.GPIO_Mode=GPIO_Mode_AF_PP;  
        GPIO_InitStrue.GPIO_Pin=GPIO_Pin_9;  
        GPIO_InitStrue.GPIO_Speed=GPIO_Speed_10MHz;  
        GPIO_Init(GPIOA,&GPIO_InitStrue);  
          
        GPIO_InitStrue.GPIO_Mode=GPIO_Mode_IN_FLOATING;  
        GPIO_InitStrue.GPIO_Pin=GPIO_Pin_10;  
        GPIO_InitStrue.GPIO_Speed=GPIO_Speed_10MHz;  
        GPIO_Init(GPIOA,&GPIO_InitStrue);  
          
        USART_InitStrue.USART_BaudRate=115200;  
        USART_InitStrue.USART_HardwareFlowControl=USART_HardwareFlowControl_None;  
        USART_InitStrue.USART_Mode=USART_Mode_Tx|USART_Mode_Rx;  
        USART_InitStrue.USART_Parity=USART_Parity_No;  
        USART_InitStrue.USART_StopBits=USART_StopBits_1;  
        USART_InitStrue.USART_WordLength=USART_WordLength_8b;  
          
        USART_Init(USART1,&USART_InitStrue);
          
        USART_Cmd(USART1,ENABLE);//使能串口1  
          
        USART_ITConfig(USART1,USART_IT_RXNE,ENABLE);//开启接收中断  
          
        NVIC_InitStrue.NVIC_IRQChannel=USART1_IRQn;  
        NVIC_InitStrue.NVIC_IRQChannelCmd=ENABLE;  
        NVIC_InitStrue.NVIC_IRQChannelPreemptionPriority=1;  
        NVIC_InitStrue.NVIC_IRQChannelSubPriority=1;  
        NVIC_Init(&NVIC_InitStrue);  
          
    }  
      
    void USART1_IRQHandler(void)  
    {  
        u8 res;  
         if(USART_GetITStatus(USART1,USART_IT_RXNE)!=RESET)  
     {  
         res= USART_ReceiveData(USART1); 	 
         USART_SendData(USART1,res);     
      }  
    }  
       
     int main(void)  
     {    
    	NVIC_PriorityGroupConfig(NVIC_PriorityGroup_2);  
        My_USART1_Init();  
         while(1);  
           
     } 

    这段程序和【STM32】串口相关配置寄存器、库函数(UART一般步骤)中的程序一模一样,几乎没有什么改动。

    区别就是,在UART实验中,USART1是和USB转串口模块连接在一起的,然后与电脑上的串口调试助手进行通信;现在改成USART1是和蓝牙模块连接在一起的,然后和手机上的蓝牙串口调试助手进行通信。

     

    展开全文
  • STM32—串口通讯详解

    万次阅读 多人点赞 2019-07-30 22:26:34
    串口通讯目录物理层协议层USART简介代码讲解 串口通讯(Serial Communication)是一种设备间非常常用的串行通讯方式,因为它简单便捷,因此大部分电子设备都支持该通讯方式,其通讯协议可分层为协议层和物理层。物理层...
  • Qt 串口通信(QSerialPort)

    万次阅读 多人点赞 2018-08-14 16:55:50
    与下位机,单片机通信少不了使用串口进行通信,Qt 也提供了串口通信的类 QSerialPort https://doc.qt.io/qt-5.9/qserialport.html //小伙伴们具体去看文档 使用的时候在 pro 添加这句导入模块 QT += serialport ...
  • STM32 串口中断总结

    万次阅读 多人点赞 2017-12-25 17:03:17
    本文以USART1为例,叙述串口中断的编程过程。 1、先来讲述一下在应用串口中断时涉及到的一些库文件。 首先对于STM32外设库文件的应用编程,misc.c和stm32f10x_rcc.c是肯定要添加到。 接下来就是我们要用到的相关...
  • 串口通信的基本知识

    万次阅读 多人点赞 2014-07-02 14:41:03
    [编辑简介]:本文介绍了串口通讯的基本概念、数据格式、通讯方式、典型的串口通讯标准等内容。 [关键词]:串口通讯,RS232,RS485,停止位,奇校验,偶校验 1 串口通讯 串口通讯(Serial Communication),是指外设和...
  • 异步串口通信

    千次下载 热门讨论 2012-07-12 22:09:19
    多线程异步串口通信, 通过底层API实现,VS2010环境编码 在本人博客中有详尽的文档说明,介绍串口通信的知识 http://blog.csdn.net/mingojiang/article/details/7713529
  • 单片机 串口编程之串口通信仿真实验

    万次阅读 多人点赞 2018-11-17 18:28:24
    单片机 串口编程之串口通信仿真实验 一、简述 记--简单的使能串口串口收发数据的例子。(使用Proteus仿真+虚拟串口调试) 代码,仿真文件打包:链接: https://pan.baidu.com/s/1nyb46fTJrYcAy_VarFdO3A 提取...
  • Java使用开源Rxtx实现串口通讯 串口开发

    千次下载 热门讨论 2014-04-13 15:48:48
    Java使用开源Rxtx实现串口通讯 串口开发,里面包含实例,下载后按自己的要求进行修改即可(仅限对java有基础的人员)。
  • C#串口操作串口操作串口操作C#串口操作串口操作串口操作C#串口操作串口操作串口操作C#串口操作串口操作串口操作C#串口操作串口操作串口操作
  • 关于串口数据的发送和接收(调试必备)

    万次阅读 多人点赞 2019-03-21 20:44:53
    对于串口的数据发送和接收,大多是都是利用串口中断来进行的,但是这样对于编程方面有一定要求,并且程序也不太好写,比如说,如果让你随意接收一段数据,然后利用串口将它发送出来,第一个需要考虑的问题就是接收...
  • 开发串口程序首先要求你的设备需要支持串口通信,可以在设备上装一个App端的串口工具来检测一下 链接:https://pan.baidu.com/s/11L4aZI9orBhbnztka6H1Og 提取码:bvot 或者在电脑端下载一个友善串口助手检测一下...
  • 一、查看本机串口信息 1. 串口是否在使用 串口在 /dev 目录中,查看串口是否在使用,可以用命令 ls -l /dev/ttyUSB0 说明: ls -l:是查看目录的命令,直接用ls或ll也可以。 ttyUSB0:是串口名,一般都是...
  • C#串口介绍以及简单串口通信程序设计和实现

    千次下载 热门讨论 2017-04-26 18:20:42
    C#串口介绍以及简单串口通信程序设计实现 源代码和串口程序介绍连接:https://www.cnblogs.com/JiYF/p/6618696.html 本站积分太贵,自己变得。。直接到连接地址下载代码 周末,没事干,写个简单的串口通信工具,也...
  • STM32串口发送数据和接收数据方式总结

    万次阅读 多人点赞 2018-05-13 20:34:22
    之前写了篇关于ESP8266使用AT指令进行互相通讯的实验,在写STM32串口接发数据的程序中,觉得有必要将之前学的有关于串口方面的使用经历加以总结。 串口发送数据: 1. 串口发送数据最直接的方式就是标准调用...
  • 几款好用的串口和网络调试助手

    万次阅读 多人点赞 2019-10-22 14:27:04
    和嵌入式厮混在一起总得用几个趁手的调试助手,这里介绍几个用过的串口和网络调试助手,各有千秋: 1.这是我最常用的,没有太花哨的界面和操作,满足基本需求。既具有串口调试功能,又具有网络调试功能。不过一般...
  • VS2010/2008/2005 MSCOMM串口控件

    千次下载 热门讨论 2011-04-29 19:00:11
    VS2010MFC没有串口控件,此压缩包里包含了串口控件相关的3个文件。mscomm32.ocx MSCOMM32.oca MSCOMM32.DEP MSCOMM.SRG 将这几个文件拷贝到一个固定的目录下然后注册就可以在MFC里正常使用串口控件了。 注册:开始->...
  • Android串口通信:串口读写

    热门讨论 2016-01-13 17:54:02
    Android 串口通信DEMO,包括JNI CPP代码,SO库等.rar,应大家要求把所需积分改了,全部开源,绝对保证能用。
  • 基于MATLAB GUI的串口通信

    万次阅读 多人点赞 2017-09-12 21:23:45
    之前学过单片机 对于串口通信比较了解 最近在学习MATLAB 发现它还可以控制串口 于是通过MATLAB 的GUI创建了一个串口通信的小软件 效果如下 如果没有单片机或者其他硬件的话 我们可以直接用软件模拟串口 ...
  • python串口工具,串口上位机

    千次阅读 2019-12-19 18:40:57
    python 使用pyserial串口库开发串口工具 之前发过用tkinter库设计的串口工具UI代码,以下为python串口的逻辑代码,已整理成模块,可以随时保存下来使用。部分函数采用中文命名,只是测试中文函数是否可运行,事实...
  • 树莓派串口

    万次阅读 2018-11-09 15:20:49
    树莓派上自带一个串口,用于连接蓝牙或是串口命令行,串口资源很少,对于嵌入式的应用来说串口设备很多,需要的串口数量也很多,因为通过USB外接串口是一个不错的选择。树莓派的 raspberry 2018.04.18 stretch版本的...
  • linux下串口通信主要有下面几个步骤 串口通信流程图 下面我会一一介绍这几个步骤。 1.打开串口 代码(串口为ttyUSB0) //打开串口 int open_port(void) { int fd; fd=open("/dev/ttyUSB0",O_RDWR | O_NOCTTY...
  • 作为嵌入式工程师,串口是必要的。通常一个电脑的U口只能使用一个USB转串口模块,也就是只能查看一路串口数据。电脑的USB口一般都是2-3个,如果加上鼠标和键盘基本上就只能冗余出一个串口,这样如果想查看两路串口...
  • 关于STC8单片机串口1、串口2、串口3、串口4的配置

    千次阅读 多人点赞 2019-07-03 17:54:33
    串口1初始化配置: void Uart1Init(void) // 9600bps@12.000MHz { SCON = 0x50; // 8位数据,可变波特率 AUXR |= 0x40; // 定时器1时钟为Fosc,即1T AUXR &= 0xFE; // 串口1选择定时器1为波特率发生器 TMOD...
  • Arduino虚拟串口串口

    千次阅读 2018-04-16 09:07:57
    #include &... //定义虚拟串口名为serial,rx为6号端口,tx为7号端口 void setup() { serial.begin(9600); //初始化虚拟串口 Serial.begin(9600); //初始化Arduino默认串口 } char a; void loo...
  • Java串口编程:串口数据的发送与监听读取

    万次阅读 多人点赞 2015-03-15 11:23:53
    本人在近期的开发工作中遇到向串口发送设备控制指令的需求,遂对串口编程进行了略微深入的钻研,在此对自己的一些心得和经验进行总结,以供大家参考与交流。 串口介绍  串口全称为串行接口,一般指COM接口,是...
  • 全汉化破解版本,简单易用,里面包含‘友善串口调试工具’和‘虚拟串口模拟器vspd6.9’,模拟出的COM1、COM2 口是相通的,往COM1发送数据,COM2能接收到,适合开发人员模拟调试,好东西要分享! winXP、win7、win8 ...

空空如也

空空如也

1 2 3 4 5 ... 20
收藏数 304,478
精华内容 121,791
关键字:

串口