executor.c revision 1.3
11.3Sandvar/* $NetBSD: executor.c,v 1.3 2024/07/06 09:53:19 andvar Exp $ */ 21.1Skamil 31.1Skamil/*- 41.1Skamil * Copyright (c) 2018 The NetBSD Foundation, Inc. 51.1Skamil * All rights reserved. 61.1Skamil * 71.1Skamil * Redistribution and use in source and binary forms, with or without 81.1Skamil * modification, are permitted provided that the following conditions 91.1Skamil * are met: 101.1Skamil * 1. Redistributions of source code must retain the above copyright 111.1Skamil * notice, this list of conditions and the following disclaimer. 121.1Skamil * 2. Redistributions in binary form must reproduce the above copyright 131.1Skamil * notice, this list of conditions and the following disclaimer in the 141.1Skamil * documentation and/or other materials provided with the distribution. 151.1Skamil * 161.1Skamil * THIS SOFTWARE IS PROVIDED BY THE NETBSD FOUNDATION, INC. AND CONTRIBUTORS 171.1Skamil * ``AS IS'' AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED 181.1Skamil * TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR 191.1Skamil * PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE FOUNDATION OR CONTRIBUTORS 201.1Skamil * BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR 211.1Skamil * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF 221.1Skamil * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS 231.1Skamil * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN 241.1Skamil * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) 251.1Skamil * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE 261.1Skamil * POSSIBILITY OF SUCH DAMAGE. 271.1Skamil */ 281.1Skamil 291.1Skamil#include <sys/cdefs.h> 301.3Sandvar__KERNEL_RCSID(0, "$NetBSD: executor.c,v 1.3 2024/07/06 09:53:19 andvar Exp $"); 311.1Skamil 321.1Skamil#include <sys/param.h> 331.1Skamil#include <sys/module.h> 341.1Skamil#include <sys/callout.h> 351.1Skamil#include <sys/once.h> 361.1Skamil 371.1Skamil/* 381.1Skamil * Check if dmesg prints 391.1Skamil * "executor <no-of-seconds-after-loading>" every second 401.1Skamil * and "executor once" exactly once in the beginning 411.1Skamil * to test this module 421.1Skamil */ 431.1Skamil 441.1SkamilMODULE(MODULE_CLASS_MISC, executor, NULL); 451.1Skamil 461.1Skamilstatic void callout_example(void *); 471.1Skamilstatic int runonce_example(void); 481.1Skamil 491.1Skamilstatic int executor_count = 0; //To hold the count of seconds 501.1Skamil 511.1Skamilstatic callout_t sc; 521.1Skamil 531.1Skamil/* Creating a variable that marks whether the function has executed or not */ 541.1Skamilstatic once_t ctl; 551.1Skamilstatic ONCE_DECL(ctl); 561.1Skamil 571.1Skamil/* 581.1Skamil * runonce_example : This function should execute only once 591.1Skamil * It should return 0 as RUN_ONCE calls the function until it returns 0. 601.1Skamil */ 611.1Skamil 621.1Skamilstatic int 631.1Skamilrunonce_example(void) { 641.1Skamil printf("executor once\n"); 651.1Skamil return 0; 661.1Skamil} 671.1Skamil 681.1Skamil/* 691.1Skamil * callout_example : This function should get executed every second. 701.1Skamil * It calls runonce_example each time. 711.3Sandvar * It prints the seconds elapsed after the module was loaded. 721.1Skamil * It reschedules the callout to the next second using callout_schedule 731.1Skamil */ 741.1Skamil 751.1Skamilstatic void 761.1Skamilcallout_example(void *arg) { 771.1Skamil RUN_ONCE(&ctl, runonce_example); 781.1Skamil executor_count++; 791.1Skamil printf("Callout %d\n", executor_count); 801.1Skamil callout_schedule(&sc, mstohz(1000)); 811.1Skamil} 821.1Skamil 831.1Skamil/* 841.1Skamil * executor_modcmd : has two tasks 851.1Skamil * On loading the module it needs to initialize a callout handle and schedule 861.1Skamil * the first callout. 871.1Skamil * On unloading the module it needs to stop and destroy the callout handle 881.1Skamil */ 891.1Skamil 901.1Skamilstatic int 911.1Skamilexecutor_modcmd(modcmd_t cmd, void *arg) 921.1Skamil{ 931.1Skamil switch(cmd) { 941.1Skamil case MODULE_CMD_INIT: 951.1Skamil printf("executor module inserted\n"); 961.2Sad callout_init(&sc, CALLOUT_MPSAFE); 971.1Skamil callout_reset(&sc, mstohz(1000), callout_example, NULL); 981.1Skamil break; 991.1Skamil case MODULE_CMD_FINI: 1001.1Skamil printf("executor module unloaded\n"); 1011.2Sad callout_halt(&sc, NULL); 1021.1Skamil callout_destroy(&sc); 1031.1Skamil break; 1041.1Skamil default: 1051.1Skamil return ENOTTY; 1061.1Skamil } 1071.1Skamil return 0; 1081.1Skamil} 109