Taskqueue : Periodic

#

Version

Freebsd

14.1.0

  • In this program, you are going to learn

  • How to schedule the taskqueue ?

 1#include<sys/param.h>
 2#include<sys/module.h>
 3#include<sys/kernel.h>
 4#include<sys/malloc.h>
 5#include<sys/queue.h>
 6#include<sys/taskqueue.h>
 7#include<sys/callout.h>
 8
 9 // Define the task structure
10static struct task my_task;
11
12 // Taskqueue handle
13static struct taskqueue *my_taskqueue;
14
15// Define callout structure
16static struct callout my_callout;
17
18 // Taskqueue handler
19static void task_handler(void *context, int pending)
20{
21	static int counter = 0;
22	counter++;
23	printf("Taskqueue excuted: counter : %d, pending : %d\n",counter,pending);
24}
25
26// Callout handler function to enqueue the task repeatedly
27static void callout_handler(void *arg)
28{
29	printf("Repeated taskqueue\n");
30
31	//Enqueue the task
32	taskqueue_enqueue(my_taskqueue,&my_task);
33
34	//Reschedule the callout for repeadted execution
35	callout_reset(&my_callout,hz,callout_handler,NULL);
36}
37
38static int event_handler(struct module *module, int event, void *arg)
39{
40	int e = 0;
41
42        switch(event)
43        {
44        case MOD_LOAD:
45		printf("Module loaded\n");
46
47		// Initialize the taskqueue (shared taskqueue thread)
48		my_taskqueue = taskqueue_create("my_taskqueue", M_NOWAIT, taskqueue_thread_enqueue, &my_taskqueue);
49		
50		// Create taskqueue thread
51		taskqueue_start_threads(&my_taskqueue,1, PI_NET, "my_taskqueue_thread");
52
53		// Initialize the task
54		TASK_INIT(&my_task, 0, task_handler, NULL);
55		
56		// Initialize and start the callout to repeatedly enqueue the task
57		callout_init(&my_callout, 1);
58		callout_reset(&my_callout,hz,callout_handler,NULL); //Repeat every second
59                break;
60
61        case MOD_UNLOAD:
62                printf("Module unloaded\n");
63
64		//Stop the taskqueue and callout
65		taskqueue_drain(my_taskqueue, &my_task);
66		callout_drain(&my_callout);
67		
68		// Free the taskqueue
69		taskqueue_free(my_taskqueue);
70                break;
71
72        default:
73                e = EOPNOTSUPP;
74                break;
75        }
76return(e);
77}
78
79static moduledata_t taskqueue_data = {
80	"taskqueue_module",
81	event_handler,
82	NULL
83};
84
85DECLARE_MODULE(taskqueue_module, taskqueue_data, SI_SUB_DRIVERS, SI_ORDER_MIDDLE);
86	
1SRCS=taskqueue.c
2KMOD=taskqueue_module
3
4.include <bsd.kmod.mk>
 1$ pwd
 2basic_device_drivers/taskqueue_periodic
 3
 4
 5$ ls
 6taskqueue.c  Makefile
 7
 8
 9$ make
10
11$ ls
12.depend.taskqueue.o       export_syms             machine                 taskqueue.c               taskqueue_module.ko
13Makefile                  i386                    opt_global.h            taskqueue.o               x86
  • Load the module using kldload

1$ kldload -v ./taskqueue_module.ko
2Loaded ./taskqueue_module.ko, id=8
  • Run kldstat command to check the loaded modules

 1$ kldstat
 2Id Refs Address                Size Name
 3 1   29 0xffffffff80200000  1f6c698 kernel
 4 2    1 0xffffffff8216e000   772c70 zfs.ko
 5 3    1 0xffffffff828e1000     7850 cryptodev.ko
 6 4    1 0xffffffff83218000     3220 intpm.ko
 7 5    1 0xffffffff8321c000     2178 smbus.ko
 8 6    1 0xffffffff8321f000     3360 uhid.ko
 9 7    1 0xffffffff83223000     3360 wmt.ko
10 8    1 0xffffffff83227000     20b8 taskqueue_module.ko
  • Run dmesg command to check the kernel logs

 1$ dmesg
 2Module loaded
 3Repeated taskqueue
 4Taskqueue excuted: counter : 1, pending : 1
 5Repeated taskqueue
 6Taskqueue excuted: counter : 2, pending : 1
 7Repeated taskqueue
 8Taskqueue excuted: counter : 3, pending : 1
 9Repeated taskqueue
10Taskqueue excuted: counter : 4, pending : 1
11Repeated taskqueue
12Taskqueue excuted: counter : 5, pending : 1
  • Unload the module using kldunload

1$ kldunload -v ./taskqueue_module.ko
2Unloading taskqueue_module.ko, id=8
  • Run kldstat command to check the loaded modules

1$ kldstat
2Id Refs Address                Size Name
3 1   27 0xffffffff80200000  1f6c698 kernel
4 2    1 0xffffffff8216e000   772c70 zfs.ko
5 3    1 0xffffffff828e1000     7850 cryptodev.ko
6 4    1 0xffffffff83218000     3220 intpm.ko
7 5    1 0xffffffff8321c000     2178 smbus.ko
8 6    1 0xffffffff8321f000     3360 uhid.ko
9 7    1 0xffffffff83223000     3360 wmt.ko
  • Run dmesg command to check the kernel logs

 1$ dmesg
 2Module loaded
 3Repeated taskqueue
 4Taskqueue excuted: counter : 1, pending : 1
 5Repeated taskqueue
 6Taskqueue excuted: counter : 2, pending : 1
 7Repeated taskqueue
 8Taskqueue excuted: counter : 3, pending : 1
 9Repeated taskqueue
10Taskqueue excuted: counter : 4, pending : 1
11Repeated taskqueue
12Taskqueue excuted: counter : 5, pending : 1
13Repeated taskqueue
14Taskqueue excuted: counter : 6, pending : 1
15Repeated taskqueue
16Taskqueue excuted: counter : 7, pending : 1
17Repeated taskqueue
18Taskqueue excuted: counter : 8, pending : 1
19Repeated taskqueue
20Taskqueue excuted: counter : 9, pending : 1
21Module unloaded