怎样建设免费网站,软件技术职业生涯规划书,湖南软装设计公司,合肥怎么做网站Q: 什么是任务#xff1f;
A: 任务可以理解为进程/线程#xff0c;创建一个任务#xff0c;就会在内存开辟一个空间。 比如#xff1a; 玩游戏#xff0c;打篮球#xff0c;开车#xff0c;都可以视为任务。 Windows 系统中的 MarkText 、谷歌浏览器、记事本#xff0…Q: 什么是任务
A: 任务可以理解为进程/线程创建一个任务就会在内存开辟一个空间。 比如 玩游戏打篮球开车都可以视为任务。 Windows 系统中的 MarkText 、谷歌浏览器、记事本都是任务。 任务通常都含有 while(1) 死循环。 任务创建与删除相关函数
xTaskCreate() 动态方式创建任务xTaskCreateStatic() 静态方式创建任务vTaskDelete() 删除任务
任务动态创建与静态创建的区别
动态创建任务的 堆栈 由系统分配而静态创建任务的 堆栈 由用户自己传递。 通常情况下使用动态方式创建任务。 xTaskCreate 函数原型 1. pvTaskCode指向任务函数的指针任务必须实现为永不返回即连续循环 2. pcName任务的名字主要是用来调试默认情况下最大长度是16 3. pvParameters指定的任务栈的大小 4. uxPriority任务优先级数值越大优先级越大和中断优先级的概念相反 5. pxCreatedTask用于返回已创建任务的句柄可以被引用。 官方案例 vTaskDelete 函数原型 只需将待删除的任务句柄传入该函数即可将该任务删除。 当传入的参数为NULL则代表删除任务自身当前正在运行的任务。 实操演示
在 C:\mjm_CubeMX_proj 路径下复制一份Cube的母版并重命名为 mjm_freeRTOS_credel_Task 打开相应的Cube文件找到左侧的Middleware -- FREERTOS然后在下方找到Task and Queues: 可见系统已经默认创建了一个任务“defaultTask”点击可以编辑 在这个弹窗里的选项其实就对应了刚刚上面 xTaskCreate 函数 的 传入参数
此处如果想要动态的创建一个任务并保持一般的优先级的话就只需要修改“Task Name和Entry Function: 以同样的方式再创建一个任务(注意此时的默认优先级是IDLE即最低所以要把他改成normal): 创建完成两个任务 在GPIO中设置PB8和PB9并拉高 然后生成代码打开Keil:
打开左侧的freertos.c:
可以找到刚刚定义的入口函数和任务函数 但是注意到创建任务的函数却不是xTaskCreate 函数 但是实际上如果跳转这个所谓的osThreadCreate函数就会发现这是Cube自动封装的一个函数里面本质上还是在调用xTaskCreate 函数 可见就是两个if区分了是否 动态创建 的情况而已。 而观察传入 xTaskCreate 函数 的参数可知Cube还封装了一个叫osThreadDef_t的结构体其中的成员正是 xTaskCreate的传入参数 那么显而易见任务的代码就写在任务函数中
void StartTaskLED_1(void const * argument)
{for(;;) //相当于一个while(1){HAL_GPIO_TogglePin(GPIOB, GPIO_PIN_8);//翻转LED1的状态osDelay(500); //一个Cube封装的Delay函数毫秒为单位}
}void StartTaskLED_2(void const * argument)
{for(;;){HAL_GPIO_TogglePin(GPIOB, GPIO_PIN_9);//翻转LED2的状态osDelay(1000);}
}
实现效果 可见LED1和LED2各自按照Delay的时间以不同的频率闪烁。
这看似是一件很正常的事情实际上这解决了一个很大的痛点在之前使用STM32裸机开发时经常会碰到“遇到一个while(1)程序就会卡死”的问题为了解决这个问题使用了中断但是中断也只是暂时的打断如果中断中有while(1)程序同样也会卡死。
但是通过FreeRTOS创建两个任务这就使得同时运行两个 while(1成为了现实