Freertos学习02-Task传入参数
一、前言
介绍了freertos具有许多特点,其中的任务调度将有助提高系统的实时性,并将各任务解耦,有助于产品的后续维护与开发,上一节介绍了freertos中关于任务的创建与删除,这一节介绍如何在创建函数的同时并传递参数。
二、传递参数
再次回顾xTaskCreate()函数的用法以及各输入参数,其中第四个输入参数"void* pvParameters"是一个空类型指针,使用空类型指针可以传入任意类型的数据,下面分别展示传入整型(int)、数组(array)、字符串(string)、结构体(struct)几种类型数据。
空类型指针:空指针和空类型指针是两个不同的概念。空指针是指一个指针变量指向的地址为空,而空类型指针是指一个指针变量的类型为空,需要注意的是空类型指针不能直接进行指针运算,因为它的类型未定义或未知。如果需要进行指针运算,我们需要将其转换为具体的指针类型。
三、示例
1.传入整型数据
1)首先定义变量testNum,并传入xTaskCreate()中,将&testNum地址强制转换为空指针类型,
int testNum = 1; xTaskCreate(mytask, "mytask", 1024, (void *)&testNum, 1, &xHandle);
2)mytask()函数接收到该变量地址,由于空类型指针无法直接参与运算,首先将它转换为int类型指针
void mytask(void *pvParam) { for (;;) { int *pInt; pInt = (int *)pvParam; printf("%d\n", *pInt); } }
完整代码如下:
#include <stdio.h> #include "driver/gpio.h" #include "freertos/FreeRTOS.h" #include "freertos/task.h" #include "sdkconfig.h" void mytask(void *pvParam) { for (;;) { int *pInt; pInt = (int *)pvParam; printf("%d\n", *pInt) } } int testNum = 1; void app_main(void) { TaskHandle_t xHandle = NULL; //任务句柄,类似任务的数字标记,识别码,名字 xTaskCreate(mytask, "mytask", 1024, (void *)&testNum, 1, &xHandle); //传入参数(void *)&testNum }
2.传入数组类型
1)首先定义数组并赋值,并将数组地址传入xTaskCreate()函数中,由于数组的名字就是数组的地址,也就是第一个数组元素的地址,所以直接在函数中写数组名即可。
int testNum[] = {4,8,12}; xTaskCreate(mytask, "mytask", 2048, (void *)testNum, 1, &xHandle);
2)在mytask任务函数中把数组中的元素全部打印出来
void mytask(void *pvParam) { for (;;) { int *pInt; pInt = (int *)pvParam; printf("%d\n", *pInt); printf("%d\n", *(pInt + 1)); printf("%d\n", *(pInt + 2)); vTaskDelay(500 / portTICK_PERIOD_MS); // 延时 } }
完整代码如下:
#include <stdio.h> #include "driver/gpio.h" #include "freertos/FreeRTOS.h" #include "freertos/task.h" #include "sdkconfig.h" void mytask(void *pvParam) { for (;;) { int *pInt; pInt = (int *)pvParam; printf("%d\n", *pInt); printf("%d\n", *(pInt + 1)); printf("%d\n", *(pInt + 2)); vTaskDelay(500 / portTICK_PERIOD_MS); // 延时 } } int testNum[] = {4, 8, 12}; void app_main(void) { TaskHandle_t xHandle = NULL; // 任务句柄,类似任务的数字标记,识别码,名字 xTaskCreate(mytask, "mytask", 2048, (void *)testNum, 1, &xHandle); // 传入参数(void *)testNum }
3.传入字符串
C语言中并没有字符串类型的变量,实际上我们可以把它理解为一个字符数组,我们一般可以这样对字符串初始化
char *message = "Hello World!"; // 上面的语句也可以拆分成下面两句 char *message; message = "Hello World!"; // 这句话看起来像是字符串复制,其实不是,只是涉及到指针操作
更常用的是:
char charArray[] = "Hello World!"; // 声明并初始化一个字符数组
或者:
char charArray[] = {'H','e','l','l','o'}; // 声明并初始化一个字符数组
综上,C语言中并不存在字符串变量类型,将其理解为字符数组,可以通过数组进行定义,也可通过指针进行初始化。
1)定义字符串Xmessage,并将字符串地址传入xTaskCreate中
char *Xmessage = "I love noob!"; xTaskCreate(mytask, "mytask", 2048, (void *)Xmessage, 1, &xHandle);
2)在任务函数中将字符串打印出来
void mytask(void *pvParam) { for (;;) { char *pInt; pInt = (char *)pvParam; printf("%s\n", pInt); vTaskDelay(500 / portTICK_PERIOD_MS); // 延时 } }
完整代码如下:
#include <stdio.h> #include "driver/gpio.h" #include "freertos/FreeRTOS.h" #include "freertos/task.h" #include "sdkconfig.h" void mytask(void *pvParam) { for (;;) { char *pInt; pInt = (char *)pvParam; printf("%s\n", pInt); vTaskDelay(500 / portTICK_PERIOD_MS); // 延时 } } char *Xmessage = "I love noob!"; void app_main(void) { TaskHandle_t xHandle = NULL; // 任务句柄,类似任务的数字标记,识别码,名字 xTaskCreate(mytask, "mytask", 2048, (void *)Xmessage, 1, &xHandle); // 传入参数(void *)Xmessage }
3.传入结构体类型
1)初始化结构体,构造一个名为xstruct的结构体,该结构体有两个成员,分别是num1和num2,d对结构体赋值并传地址入xTaskCreate()函数
typedef struct Xstruct { int num1; int num2; } xstruct; xstruct xtest = {2, 4}; xTaskCreate(mytask, "mytask", 2048, (void *)&xtest, 1, &xHandle);
2)在任务函数中打印结构体成员的数值
void mytask(void *pvParam) { for (;;) { xstruct *pInt; pInt = (xstruct *)pvParam; printf("First num is %d\n", pInt->num1); printf("Second num is %d\n", pInt->num2); vTaskDelay(500 / portTICK_PERIOD_MS); // 延时 } }
完整代码如下:
#include <stdio.h> #include "driver/gpio.h" #include "freertos/FreeRTOS.h" #include "freertos/task.h" #include "sdkconfig.h" typedef struct Xstruct { int num1; int num2; } xstruct; void mytask(void *pvParam) { for (;;) { xstruct *pInt; pInt = (xstruct *)pvParam; printf("First num is %d\n", pInt->num1); printf("Second num is %d\n", pInt->num2); vTaskDelay(500 / portTICK_PERIOD_MS); // 延时 } } xstruct xtest = {2, 4}; void app_main(void) { TaskHandle_t xHandle = NULL; // 任务句柄,类似任务的数字标记,识别码,名字 xTaskCreate(mytask, "mytask", 2048, (void *)&xtest, 1, &xHandle); // 传入参数 }
THE END!
本文作者:seekwhale13
本文链接:https://www.cnblogs.com/seekwhale13/p/17504220.html
版权声明:本作品采用知识共享署名-非商业性使用-禁止演绎 2.5 中国大陆许可协议进行许可。
【推荐】国内首个AI IDE,深度理解中文开发场景,立即下载体验Trae
【推荐】编程新体验,更懂你的AI,立即体验豆包MarsCode编程助手
【推荐】抖音旗下AI助手豆包,你的智能百科全书,全免费不限次数
【推荐】轻量又高性能的 SSH 工具 IShell:AI 加持,快人一步