RT-Thread入门



  • 在写这篇笔记之前,先了解了freeRTOS,并尝试从头到尾把freeRTOS内核实现一遍,以追求更好的理解,写内核的过程十分艰难,到了需要用汇编语言编写的时候,32的汇编指令集拦住了我,之前虽然了解过汇编语言,但了解还是过浅,等不急的我就先把系统编写的原理顺了一遍。freeRTOS还没应用的时候,我发现了RT-thread....

    大概了解了一下二者的区别,从组件上
    0_1608213508318_ac5dd381-1f7c-47f9-939f-61d1b7b4f173-image.png
    0_1608213538724_027c31e7-182a-4220-a4c5-6f30aff2b777-image.png
    0_1608213563318_7cfaaebc-485c-4c70-8fd5-65c7aa54dd2a-image.png

    从内核本身上
    0_1608213586903_798dc07e-b5d8-4f0e-bb2b-cc87cedbfef7-image.png

    而且RT-thread是国产物联网系统,中文资料较多,国内开发环境比较好,有自己的开发软件RT-Thread Studio

    在了解系统之前,我编写时一般采用轮询的方式或者前后台系统,在很多时候,觉得CPU忙不过来,希望CPU能同时处理多件事情,前一段时间,和同学一起做了一个STC控制的时钟,多加了一些功能,并且用LCD做了很多显示界面和菜单,加了流水灯和蜂鸣器,明显能够感受到裸机系统在处理任务时的迟钝。

    RT-thread的多线程恰巧能够解决这个问题,在熟悉了一遍RT-thread内核之后,大致了解了内核的工作原理,编写一个实际的程序时,只需要先利用CubeMX初始化,然后将时钟,GPIO,中断等等相关的初始化函数移植到RT-thread系统中,建立线程,开启调度即可。

    于是从最简单的工程开始,进行点灯实验

    开发板上的LED是三合一的RGB灯,分别建立三个线程,每个线程控制一个LED闪烁,而绿灯闪烁间隔是1秒,蓝灯闪烁间隔2秒,红灯闪烁间隔3秒,如果工作正常的话,颜色显示应该为:
    白、紫、黄、(灭)、白、蓝、黄、红、白、蓝、绿、(灭)..................

    主函数代码如下:
    #include <rtthread.h>

    #define DBG_TAG "main"
    #define DBG_LVL DBG_LOG
    #include <rtdbg.h>
    #include "stm32f1xx_hal.h"

    #define LED1_Pin GPIO_PIN_0
    #define LED1_GPIO_Port GPIOB
    #define LED2_Pin GPIO_PIN_1
    #define LED2_GPIO_Port GPIOB
    #define LED3_Pin GPIO_PIN_5
    #define LED3_GPIO_Port GPIOB
    #define THREAD_PRIORITY 2
    #define THREAD_TIMESLICE 5

    static void MX_GPIO_Init(void);

    static void thread1_entry(void *parameter){

    while(1){
        HAL_GPIO_TogglePin(GPIOB,LED1_Pin);
        rt_thread_delay(1000);
        HAL_GPIO_TogglePin(GPIOB,LED1_Pin);
        rt_thread_delay(1000);
    }
    

    }

    static void thread2_entry(void *parameter){

    while(1){
        HAL_GPIO_TogglePin(GPIOB,LED2_Pin);
        rt_thread_delay(2000);
        HAL_GPIO_TogglePin(GPIOB,LED2_Pin);
        rt_thread_delay(2000);
    }
    

    }

    static void thread3_entry(void *parameter){

    while(1){
        HAL_GPIO_TogglePin(GPIOB,LED3_Pin);
        rt_thread_delay(3000);
        HAL_GPIO_TogglePin(GPIOB,LED3_Pin);
        rt_thread_delay(3000);
    }
    

    }

    static char thread1_stack[1024];
    static struct rt_thread thread1;
    static char thread2_stack[1024];
    static struct rt_thread thread2;
    static char thread3_stack[1024];
    static struct rt_thread thread3;

    int main(void)
    {
    int count = 1;

    MX_GPIO_Init();
    
    rt_thread_init(&thread1,
                                     "thread1",
                                     thread1_entry,
                                     RT_NULL,
                                     &thread1_stack[0],
                                     sizeof(thread1_stack),
                                     THREAD_PRIORITY-1,THREAD_TIMESLICE
        );
        rt_thread_startup(&thread1);
    
        rt_thread_init(&thread2,
                                     "thread2",
                                     thread2_entry,
                                     RT_NULL,
                                     &thread2_stack[0],
                                     sizeof(thread2_stack),
                                     THREAD_PRIORITY,THREAD_TIMESLICE
        );
        rt_thread_startup(&thread2);
    
        rt_thread_init(&thread3,
                                     "thread3",
                                     thread3_entry,
                                     RT_NULL,
                                     &thread3_stack[0],
                                     sizeof(thread3_stack),
                                     THREAD_PRIORITY+1,THREAD_TIMESLICE
        );
        rt_thread_startup(&thread3);
    
    while (count++)
    {
        LOG_D("Hello RT-Thread!");
        rt_thread_mdelay(1000);
    }
    
    return RT_EOK;
    

    }

    static void MX_GPIO_Init(void)
    {
    GPIO_InitTypeDef GPIO_InitStruct = {0};

    /* GPIO Ports Clock Enable */
    __HAL_RCC_GPIOE_CLK_ENABLE();
    __HAL_RCC_GPIOC_CLK_ENABLE();
    __HAL_RCC_GPIOA_CLK_ENABLE();
    __HAL_RCC_GPIOB_CLK_ENABLE();
    __HAL_RCC_GPIOD_CLK_ENABLE();

    /*Configure GPIO pin Output Level */
    HAL_GPIO_WritePin(GPIOB, LED1_Pin|LED2_Pin|LED3_Pin, GPIO_PIN_SET);

    /*Configure GPIO pins : PE2 PE3 PE4 PE5
    PE6 PE7 PE8 PE9
    PE10 PE11 PE12 PE13
    PE14 PE15 PE0 PE1 */
    GPIO_InitStruct.Pin = GPIO_PIN_2|GPIO_PIN_3|GPIO_PIN_4|GPIO_PIN_5
    |GPIO_PIN_6|GPIO_PIN_7|GPIO_PIN_8|GPIO_PIN_9
    |GPIO_PIN_10|GPIO_PIN_11|GPIO_PIN_12|GPIO_PIN_13
    |GPIO_PIN_14|GPIO_PIN_15|GPIO_PIN_0|GPIO_PIN_1;
    GPIO_InitStruct.Mode = GPIO_MODE_ANALOG;
    HAL_GPIO_Init(GPIOE, &GPIO_InitStruct);

    /*Configure GPIO pins : PC13 PC0 PC1 PC2
    PC3 PC4 PC5 PC6
    PC7 PC8 PC9 PC10
    PC11 PC12 */
    GPIO_InitStruct.Pin = GPIO_PIN_13|GPIO_PIN_0|GPIO_PIN_1|GPIO_PIN_2
    |GPIO_PIN_3|GPIO_PIN_4|GPIO_PIN_5|GPIO_PIN_6
    |GPIO_PIN_7|GPIO_PIN_8|GPIO_PIN_9|GPIO_PIN_10
    |GPIO_PIN_11|GPIO_PIN_12;
    GPIO_InitStruct.Mode = GPIO_MODE_ANALOG;
    HAL_GPIO_Init(GPIOC, &GPIO_InitStruct);

    /*Configure GPIO pins : PA0 PA1 PA2 PA3
    PA4 PA5 PA6 PA7
    PA8 PA9 PA10 PA11
    PA12 PA15 */
    GPIO_InitStruct.Pin = GPIO_PIN_0|GPIO_PIN_1|GPIO_PIN_2|GPIO_PIN_3
    |GPIO_PIN_4|GPIO_PIN_5|GPIO_PIN_6|GPIO_PIN_7
    |GPIO_PIN_8|GPIO_PIN_9|GPIO_PIN_10|GPIO_PIN_11
    |GPIO_PIN_12|GPIO_PIN_15;
    GPIO_InitStruct.Mode = GPIO_MODE_ANALOG;
    HAL_GPIO_Init(GPIOA, &GPIO_InitStruct);

    /*Configure GPIO pins : LED1_Pin LED2_Pin LED3_Pin */
    GPIO_InitStruct.Pin = LED1_Pin|LED2_Pin|LED3_Pin;
    GPIO_InitStruct.Mode = GPIO_MODE_OUTPUT_PP;
    GPIO_InitStruct.Pull = GPIO_NOPULL;
    GPIO_InitStruct.Speed = GPIO_SPEED_FREQ_LOW;
    HAL_GPIO_Init(GPIOB, &GPIO_InitStruct);

    /*Configure GPIO pins : PB2 PB10 PB11 PB12
    PB13 PB14 PB15 PB3
    PB4 PB6 PB7 PB8
    PB9 */
    GPIO_InitStruct.Pin = GPIO_PIN_2|GPIO_PIN_10|GPIO_PIN_11|GPIO_PIN_12
    |GPIO_PIN_13|GPIO_PIN_14|GPIO_PIN_15|GPIO_PIN_3
    |GPIO_PIN_4|GPIO_PIN_6|GPIO_PIN_7|GPIO_PIN_8
    |GPIO_PIN_9;
    GPIO_InitStruct.Mode = GPIO_MODE_ANALOG;
    HAL_GPIO_Init(GPIOB, &GPIO_InitStruct);

    /*Configure GPIO pins : PD8 PD9 PD10 PD11
    PD12 PD13 PD14 PD15
    PD0 PD1 PD2 PD3
    PD4 PD5 PD6 PD7 */
    GPIO_InitStruct.Pin = GPIO_PIN_8|GPIO_PIN_9|GPIO_PIN_10|GPIO_PIN_11
    |GPIO_PIN_12|GPIO_PIN_13|GPIO_PIN_14|GPIO_PIN_15
    |GPIO_PIN_0|GPIO_PIN_1|GPIO_PIN_2|GPIO_PIN_3
    |GPIO_PIN_4|GPIO_PIN_5|GPIO_PIN_6|GPIO_PIN_7;
    GPIO_InitStruct.Mode = GPIO_MODE_ANALOG;
    HAL_GPIO_Init(GPIOD, &GPIO_InitStruct);

    }

    编译成功
    0_1608213678705_fad1009f-043c-434e-bdfb-7eabe39432ee-image.png

    烧录,现象正确,系统工作非常稳定。
    0_1608213665777_5e10ccb3-661b-4fdc-b44d-96f6a852bf82-image.png

    之前听说过RT-thread的debug功能相当好用,还会继续深入学习。



  • Cube配置也可以发一下,我的stm32cubemx里面好像只有FreeRTOS



  • FreeRTOS和UCOS不能用SPI和IIC是指不能用它硬件本身的吗?



  • @zongjie cube只能配FreeRTOS,配RT-thread要用RT_Thread Studio,UCOS要手动移植



  • 我看网上好像可以用cube配置RT-Thread的:https://blog.csdn.net/morixinguan/article/details/100166441



  • @zongjie SPI不清楚,32的IIC好像有缺陷?有时候硬件IIC好像应答不了


 

Copyright © 2018 bbs.dian.org.cn All rights reserved.

Looks like your connection to Dian was lost, please wait while we try to reconnect.