1 1.7 pgoyette /* $NetBSD: k_helper.c,v 1.7 2020/02/22 19:54:35 pgoyette Exp $ */ 2 1.1 jmmv /* 3 1.1 jmmv * Copyright (c) 2008 The NetBSD Foundation, Inc. 4 1.1 jmmv * All rights reserved. 5 1.1 jmmv * 6 1.1 jmmv * Redistribution and use in source and binary forms, with or without 7 1.1 jmmv * modification, are permitted provided that the following conditions 8 1.1 jmmv * are met: 9 1.1 jmmv * 1. Redistributions of source code must retain the above copyright 10 1.1 jmmv * notice, this list of conditions and the following disclaimer. 11 1.1 jmmv * 2. Redistributions in binary form must reproduce the above copyright 12 1.1 jmmv * notice, this list of conditions and the following disclaimer in the 13 1.1 jmmv * documentation and/or other materials provided with the distribution. 14 1.1 jmmv * 15 1.1 jmmv * THIS SOFTWARE IS PROVIDED BY THE NETBSD FOUNDATION, INC. AND 16 1.1 jmmv * CONTRIBUTORS ``AS IS'' AND ANY EXPRESS OR IMPLIED WARRANTIES, 17 1.1 jmmv * INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF 18 1.1 jmmv * MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. 19 1.1 jmmv * IN NO EVENT SHALL THE FOUNDATION OR CONTRIBUTORS BE LIABLE FOR ANY 20 1.1 jmmv * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL 21 1.1 jmmv * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE 22 1.1 jmmv * GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS 23 1.1 jmmv * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER 24 1.1 jmmv * IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR 25 1.1 jmmv * OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN 26 1.1 jmmv * IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. 27 1.1 jmmv */ 28 1.1 jmmv 29 1.1 jmmv #include <sys/cdefs.h> 30 1.7 pgoyette __KERNEL_RCSID(0, "$NetBSD: k_helper.c,v 1.7 2020/02/22 19:54:35 pgoyette Exp $"); 31 1.1 jmmv 32 1.1 jmmv #include <sys/param.h> 33 1.1 jmmv #include <sys/kernel.h> 34 1.1 jmmv #include <sys/module.h> 35 1.1 jmmv #include <sys/sysctl.h> 36 1.7 pgoyette #include <sys/evcnt.h> 37 1.1 jmmv 38 1.2 jmmv #include <prop/proplib.h> 39 1.2 jmmv 40 1.1 jmmv MODULE(MODULE_CLASS_MISC, k_helper, NULL); 41 1.1 jmmv 42 1.1 jmmv /* --------------------------------------------------------------------- */ 43 1.1 jmmv /* Sysctl interface to query information about the module. */ 44 1.1 jmmv /* --------------------------------------------------------------------- */ 45 1.1 jmmv 46 1.2 jmmv /* TODO: Change the integer variables below that represent booleans to 47 1.2 jmmv * bools, once sysctl(8) supports CTLTYPE_BOOL nodes. */ 48 1.2 jmmv 49 1.1 jmmv static int present = 1; 50 1.2 jmmv static int prop_str_ok; 51 1.2 jmmv static char prop_str_val[128]; 52 1.2 jmmv static int prop_int_ok; 53 1.4 pgoyette static int64_t prop_int_val; 54 1.4 pgoyette static int prop_int_load; 55 1.1 jmmv 56 1.7 pgoyette static struct evcnt my_counter = 57 1.7 pgoyette EVCNT_INITIALIZER(EVCNT_TYPE_MISC, NULL, "k_helper", "my_counter"); 58 1.7 pgoyette 59 1.7 pgoyette EVCNT_ATTACH_STATIC(my_counter); 60 1.7 pgoyette 61 1.1 jmmv #define K_HELPER 0x12345678 62 1.1 jmmv #define K_HELPER_PRESENT 0 63 1.2 jmmv #define K_HELPER_PROP_STR_OK 1 64 1.2 jmmv #define K_HELPER_PROP_STR_VAL 2 65 1.2 jmmv #define K_HELPER_PROP_INT_OK 3 66 1.2 jmmv #define K_HELPER_PROP_INT_VAL 4 67 1.4 pgoyette #define K_HELPER_PROP_INT_LOAD 5 68 1.1 jmmv 69 1.1 jmmv SYSCTL_SETUP(sysctl_k_helper_setup, "sysctl k_helper subtree setup") 70 1.1 jmmv { 71 1.1 jmmv 72 1.1 jmmv sysctl_createv(clog, 0, NULL, NULL, 73 1.1 jmmv CTLFLAG_PERMANENT, 74 1.1 jmmv CTLTYPE_NODE, "k_helper", NULL, 75 1.1 jmmv NULL, 0, NULL, 0, 76 1.1 jmmv CTL_VENDOR, K_HELPER, CTL_EOL); 77 1.1 jmmv 78 1.1 jmmv sysctl_createv(clog, 0, NULL, NULL, 79 1.1 jmmv CTLFLAG_PERMANENT, 80 1.1 jmmv CTLTYPE_INT, "present", 81 1.1 jmmv SYSCTL_DESCR("Whether the module was loaded or not"), 82 1.1 jmmv NULL, 0, &present, 0, 83 1.1 jmmv CTL_VENDOR, K_HELPER, K_HELPER_PRESENT, CTL_EOL); 84 1.2 jmmv 85 1.2 jmmv sysctl_createv(clog, 0, NULL, NULL, 86 1.2 jmmv CTLFLAG_PERMANENT, 87 1.2 jmmv CTLTYPE_INT, "prop_str_ok", 88 1.2 jmmv SYSCTL_DESCR("String property's validity"), 89 1.2 jmmv NULL, 0, &prop_str_ok, 0, 90 1.2 jmmv CTL_VENDOR, K_HELPER, K_HELPER_PROP_STR_OK, CTL_EOL); 91 1.2 jmmv 92 1.2 jmmv sysctl_createv(clog, 0, NULL, NULL, 93 1.2 jmmv CTLFLAG_PERMANENT, 94 1.2 jmmv CTLTYPE_STRING, "prop_str_val", 95 1.2 jmmv SYSCTL_DESCR("String property's value"), 96 1.6 dsl NULL, 0, prop_str_val, 0, 97 1.2 jmmv CTL_VENDOR, K_HELPER, K_HELPER_PROP_STR_VAL, CTL_EOL); 98 1.2 jmmv 99 1.2 jmmv sysctl_createv(clog, 0, NULL, NULL, 100 1.2 jmmv CTLFLAG_PERMANENT, 101 1.2 jmmv CTLTYPE_INT, "prop_int_ok", 102 1.2 jmmv SYSCTL_DESCR("String property's validity"), 103 1.2 jmmv NULL, 0, &prop_int_ok, 0, 104 1.2 jmmv CTL_VENDOR, K_HELPER, K_HELPER_PROP_INT_OK, CTL_EOL); 105 1.2 jmmv 106 1.2 jmmv sysctl_createv(clog, 0, NULL, NULL, 107 1.2 jmmv CTLFLAG_PERMANENT, 108 1.4 pgoyette CTLTYPE_QUAD, "prop_int_val", 109 1.2 jmmv SYSCTL_DESCR("String property's value"), 110 1.2 jmmv NULL, 0, &prop_int_val, 0, 111 1.2 jmmv CTL_VENDOR, K_HELPER, K_HELPER_PROP_INT_VAL, CTL_EOL); 112 1.4 pgoyette 113 1.4 pgoyette sysctl_createv(clog, 0, NULL, NULL, 114 1.4 pgoyette CTLFLAG_PERMANENT, 115 1.4 pgoyette CTLTYPE_INT, "prop_int_load", 116 1.4 pgoyette SYSCTL_DESCR("Status of recursive modload"), 117 1.4 pgoyette NULL, 0, &prop_int_load, 0, 118 1.4 pgoyette CTL_VENDOR, K_HELPER, K_HELPER_PROP_INT_LOAD, CTL_EOL); 119 1.1 jmmv } 120 1.1 jmmv 121 1.1 jmmv /* --------------------------------------------------------------------- */ 122 1.1 jmmv /* Module management. */ 123 1.1 jmmv /* --------------------------------------------------------------------- */ 124 1.1 jmmv 125 1.1 jmmv static 126 1.1 jmmv int 127 1.2 jmmv k_helper_init(prop_dictionary_t props) 128 1.1 jmmv { 129 1.2 jmmv prop_object_t p; 130 1.2 jmmv 131 1.2 jmmv p = prop_dictionary_get(props, "prop_str"); 132 1.2 jmmv if (p == NULL) 133 1.2 jmmv prop_str_ok = 0; 134 1.2 jmmv else if (prop_object_type(p) != PROP_TYPE_STRING) 135 1.2 jmmv prop_str_ok = 0; 136 1.2 jmmv else { 137 1.2 jmmv const char *msg = prop_string_cstring_nocopy(p); 138 1.2 jmmv if (msg == NULL) 139 1.2 jmmv prop_str_ok = 0; 140 1.2 jmmv else { 141 1.2 jmmv strlcpy(prop_str_val, msg, sizeof(prop_str_val)); 142 1.2 jmmv prop_str_ok = 1; 143 1.2 jmmv } 144 1.2 jmmv } 145 1.2 jmmv if (!prop_str_ok) 146 1.2 jmmv strlcpy(prop_str_val, "", sizeof(prop_str_val)); 147 1.2 jmmv 148 1.2 jmmv p = prop_dictionary_get(props, "prop_int"); 149 1.2 jmmv if (p == NULL) 150 1.2 jmmv prop_int_ok = 0; 151 1.2 jmmv else if (prop_object_type(p) != PROP_TYPE_NUMBER) 152 1.2 jmmv prop_int_ok = 0; 153 1.2 jmmv else { 154 1.2 jmmv prop_int_val = prop_number_integer_value(p); 155 1.2 jmmv prop_int_ok = 1; 156 1.2 jmmv } 157 1.2 jmmv if (!prop_int_ok) 158 1.2 jmmv prop_int_val = -1; 159 1.1 jmmv 160 1.4 pgoyette p = prop_dictionary_get(props, "prop_recurse"); 161 1.4 pgoyette if (p != NULL && prop_object_type(p) == PROP_TYPE_STRING) { 162 1.4 pgoyette const char *recurse_name = prop_string_cstring_nocopy(p); 163 1.4 pgoyette if (recurse_name != NULL) 164 1.4 pgoyette prop_int_load = module_load(recurse_name, 165 1.4 pgoyette MODCTL_NO_PROP, NULL, MODULE_CLASS_ANY); 166 1.4 pgoyette else 167 1.4 pgoyette prop_int_load = -1; 168 1.4 pgoyette } else 169 1.4 pgoyette prop_int_load = -2; 170 1.4 pgoyette 171 1.1 jmmv return 0; 172 1.1 jmmv } 173 1.1 jmmv 174 1.1 jmmv static 175 1.1 jmmv int 176 1.1 jmmv k_helper_fini(void *arg) 177 1.1 jmmv { 178 1.1 jmmv 179 1.1 jmmv return 0; 180 1.1 jmmv } 181 1.1 jmmv 182 1.1 jmmv static 183 1.1 jmmv int 184 1.1 jmmv k_helper_modcmd(modcmd_t cmd, void *arg) 185 1.1 jmmv { 186 1.1 jmmv int ret; 187 1.1 jmmv 188 1.1 jmmv switch (cmd) { 189 1.1 jmmv case MODULE_CMD_INIT: 190 1.1 jmmv ret = k_helper_init(arg); 191 1.1 jmmv break; 192 1.1 jmmv 193 1.1 jmmv case MODULE_CMD_FINI: 194 1.1 jmmv ret = k_helper_fini(arg); 195 1.1 jmmv break; 196 1.1 jmmv 197 1.1 jmmv case MODULE_CMD_STAT: 198 1.1 jmmv default: 199 1.1 jmmv ret = ENOTTY; 200 1.1 jmmv } 201 1.1 jmmv 202 1.1 jmmv return ret; 203 1.1 jmmv } 204