0
  • 聊天消息
  • 系统消息
  • 评论与回复
登录后你可以
  • 下载海量资料
  • 学习在线课程
  • 观看技术视频
  • 写文章/发帖/加入社区
会员中心
创作中心

完善资料让更多小伙伴认识你,还能领取20积分哦,立即完善>

3天内不再提示

RTOS多线程访问同一硬件(如UART)的方法

黄工的嵌入式技术圈 来源:黄工的嵌入式技术圈 2020-03-12 11:28 次阅读

读者*石 三*问:博主可以介绍下在RTOS下多个任务访问同一硬件的方法吗?比如说,多个任务都要用到串口打印信息

我的回答是:使用互斥量、队列两种方式都能解决访问冲突的问题。

多线程访问同一串行硬件在许多系统中经常使用,如多个线程都使用UART收发数据、多个线程使用读写SPI_FLASH、I2C_E2PROM,CAN总线收发数据等······

如果每个线程都同时抢占同一串口去读写操作,那么很容易出现问题。为了解决其中的冲突问题,就需要使用一定的办法。下面以UART为例,基于FreeRTOS讲述一下基本的互斥量和队列方式的解决方法。

Ⅰ互斥访问方法

互斥量:是一个可以处于两态之一的变量:解锁和加锁。

原理:创建一个互斥量,线程A在需要占用资源(使用UART发送数据),把资源(UART)占用。此时,线程B及其他线程就不能占用该资源。当线程A使用完资源(UART发送完数据),释放资源,其他线程就可以抢占该资源。

创建互斥量

线程A占用资源

使用资源(发送数据)

线程A释放资源

优先级高的线程B占用资源

使用资源

线程B释放资源

依次,优先级线程占用资源

代码:

//创建互斥量资源 SemaphoreHandle_t xSemaphore = NULL;xSemaphore = xSemaphoreCreateMutex(); void TaskA(void *pvParameters){ for(;;) { //占用资源 if(xSemaphoreTake(xSemaphore, 10 ) == pdTRUE) { //使用资源(发送数据) USART_SendNByte(); //释放资源 xSemaphoreGive(xSemaphore); } }}

信号量与互斥量区别:

信号量:多线程同步使用的;一个线程完成某个动作后通过信号告诉别的线程,别的线程才可以执行某些动作;

互斥量:多线程互斥使用的;一个线程占用某个资源,那么别的线程就无法访问,直到该线程离开,其他线程才可以访问该资源;

Ⅱ队列操作方法

队列操作方法就是FIFO,先入先出的原理。比如:线程A要使用UART发送一串数据,将其加入队列;接着线程B也要使用UART发送一串数据。

那么,线程A将这串数据加入队列,接着线程B又将要发送的一串数据加入队列。

在另外一个UART发送的线程中,从队列中按照FIFO方式读取队列里面的数据,依次发送出去即可。

创建一个队列(发送数据队列)

创建一个任务(UART发送数据线程)

线程A加入队列

线程B加入队列

另外一边的线程,依次读取队列数据,使用UART发送出去。

代码:

QueueHandle_t xQueue;xQueue = xQueueCreate(QUEUE_LENGTH, QUEUE_ITEM_SIZE);xTaskCreate(UART_Send_Task, "UART_Send", STACK_SIZE, NULL, TASK_PRIORITY, NULL); void TaskA(void *pvParameters){ for(;;) { //线程相关操作 //加入队列 xQueueSend(xQueue, &TaskA_Buf, 10) }} void TaskB(void *pvParameters){ for(;;) { //线程相关操作 //加入队列 xQueueSend(xQueue, &TaskB_Buf, 10) }} void UART_Send_Task(void *pvParameters){ for(;;) { //循环读取队列BUF if(xQueueReceive(xQueue, &Buf, 10) == pdTRUE) { USART_SendNByte(&Buf); } }}

以上两种方法是常用的,希望大家都掌握一下。上述仅让大家掌握原理,代码不宜直接复制粘贴使用。

声明:本文内容及配图由入驻作者撰写或者入驻合作网站授权转载。文章观点仅代表作者本人,不代表电子发烧友网立场。文章及其配图仅供工程师学习之用,如有内容侵权或者其他违规问题,请联系本站处理。 举报投诉
  • uart
    +关注

    关注

    22

    文章

    1227

    浏览量

    101165
  • 多线程
    +关注

    关注

    0

    文章

    277

    浏览量

    19919
  • RTOS
    +关注

    关注

    21

    文章

    809

    浏览量

    119414
  • 串口打印
    +关注

    关注

    0

    文章

    10

    浏览量

    3081
收藏 人收藏

    评论

    相关推荐

    socket 多线程编程实现方法

    是指在同一个进程中运行多个线程,每个线程可以独立执行任务。线程共享进程的资源,内存空间和文件句柄,但每个
    的头像 发表于 11-12 14:16 203次阅读

    Python中多线程和多进程的区别

    Python作为种高级编程语言,提供了多种并发编程的方式,其中多线程与多进程是最常见的两种方式之。在本文中,我们将探讨Python中多线程与多进程的概念、区别以及如何使用
    的头像 发表于 10-23 11:48 313次阅读
    Python中<b class='flag-5'>多线程</b>和多进程的区别

    ESP32会不会有多线程问题,需要加锁吗?

    ESP32会不会有多线程问题,需要加锁吗
    发表于 07-19 08:05

    ESP8266 RTOS SDK版本1.4.0如何从UART0获取数据?

    我需要在 RTOS SDK ( 1.4.0 ) 下为我ESP8266项目构建UART 控制台例程(作为线程),用于调试目的,但是,我无法使用 scanf 或 getchar 从
    发表于 07-12 06:52

    多线程设计模式到对 CompletableFuture 的应用

    最近在开发 延保服务 频道页时,为了提高查询效率,使用到了多线程技术。为了对多线程方案设计有更加充分的了解,在业余时间读完了《图解 Java 多线程设计模式》这本书,觉得收获良多。本篇文章将介绍其中
    的头像 发表于 06-26 14:18 265次阅读
    从<b class='flag-5'>多线程</b>设计模式到对 CompletableFuture 的应用

    bootloader开多线程做引导程序,跳app初始化后直接进hardfualt,为什么?

    标题,想做个远程升级的项目,bootloader引导区域和app都是开多线程跑的,就是自己写了个小的任务调度器,没什么功能主要是想让程序快速的响应,延时不会对其他程序造成堵塞,程序测试
    发表于 04-18 06:07

    鸿蒙原生应用开发-ArkTS语言基础类库多线程并发概述

    系列复杂偶发的问题,同时并发度也相对较高,因此得到了广泛的支持和使用,也是当前ArkTS语言选择的并发模型。 由于Actor模型的内存隔离特性,所以需要进行跨线程的数据序列化传输。 、数据传输
    发表于 03-28 14:35

    java实现多线程的几种方式

    的CompletableFuture 、继承Thread类 继承Thread类是实现多线程的最基本方式,只需创建个类并继承Thread类,重写run()方法即可。 ``
    的头像 发表于 03-14 16:55 574次阅读

    基于RTOS的应用进程中的典型线程

    RTOS中的关键因素是最小的中断延迟和最小的线程切换延迟。RTOS的价值在于它的响应速度或可预测性,而不是它在给定时间段内可以执行的工作量。
    发表于 03-05 09:32 521次阅读
    基于<b class='flag-5'>RTOS</b>的应用进程中的典型<b class='flag-5'>线程</b>

    AT socket可以多线程调用吗?

    请问AT socket 可以多线程调用吗? 有互锁机制吗,还是要自己做互锁。
    发表于 03-01 08:22

    请问RTOS USBSetuPcb回调函数是在中断还是单独线程中处理的?

    中生成另线程来并行处理 UsbRequest? 传达设置的般信息: (这不是我的代码,但传达了结构,USB和UART设置正确) appThread_Entry () {a
    发表于 02-23 06:10

    你还是分不清多进程和多线程吗?文搞懂!

    你还是分不清多进程和多线程吗?文搞懂! 多进程和多线程是并发编程中常见的两个概念,它们都可以用于提高程序的性能和效率。但是它们的实现方式和使用场景略有不同。 1. 多进程: 多进程指的是在操作系统
    的头像 发表于 12-19 16:07 538次阅读

    redis多线程还能保证线程安全吗

    是单线程的,多个客户端请求会按序执行,每个请求使用线程完成,这样可以避免多线程之间的竞争条件和锁等带来的开销。但是,由于Redis是存储内存中的数据的,当多个客户端同时对
    的头像 发表于 12-05 10:28 1683次阅读

    redis使用多线程处理操作命令

    Redis 是个使用多线程处理操作命令的开源内存数据库系统。它以其高性能、可扩展性和灵活性而闻名,通常被用作缓存、消息代理和数据存储等各种应用场景。在本文中,我们将详尽、详实、细致地探
    的头像 发表于 12-05 10:25 544次阅读

    mfc多线程编程实例

    (图形用户界面)应用程序的开发。在这篇文章中,我们将重点介绍MFC中的多线程编程。 多线程编程在软件开发中非常重要,它可以实现程序的并发执行,提高程序的效率和响应速度。MFC提供了丰富的多线程支持,可以轻松地实现
    的头像 发表于 12-01 14:29 1421次阅读