Date: Sat, 27 Jul 2013 00:46:09 -0400 From: ret val <retval42@gmail.com> To: freebsd-drivers@freebsd.org Subject: mysterious locking issue Message-ID: <CAHORHL=yF3V2--HxuahNDQjYRwThKZY0_gUXk0SsZA8gu8FDAQ@mail.gmail.com>
next in thread | raw e-mail | index | archive | help
--bcaec51b1b6f215daa04e276f0ae Content-Type: text/plain; charset=ISO-8859-1 I'm working on porting a driver form Linux that uses the usermode helper API to call a user land program from the driver. Yes, I know this is ugly. Yes, I'm sure sure there would of been many better other ways to go about this... For right now I'm just doing a straight port. Anyway, I working on my own routine for this but unfortunately I get a kernel panic on boot when my module is loaded. Oddly enough it works fine if I load it by hand after boot. I get the following: panic: mutex Giant owned at /usr/src/sys/kern/kern_thread.c:616 The backtrace looks like: panic _mtx_assert thread_single kern_execve event_handler Ive tried switching to SI_SUB_EXEC without any luck. Does anyone know how to go about fixing this? I cant seem to wrap my head around this. Incase I cant attach my code, here it is: #include <sys/param.h> #include <sys/module.h> #include <sys/kernel.h> #include <sys/systm.h> #include <sys/syscallsubr.h> #include <sys/imgact.h> #include <vm/vm_extern.h> #include <sys/kthread.h> #include <sys/proc.h> int DEBUG=1; static int make_args(struct image_args *args, char *fname, char **argv, char **envv) { int i; size_t length; memset(args, 0, sizeof(struct image_args)); if(exec_alloc_args(args) != 0) { if(DEBUG) { printf("exec_alloc_args() failed\n"); uprintf("exec_alloc_args() failed\n"); } return ENOMEM; } // fname args->fname = args->buf; length = 1 + strlen(fname); memcpy(args->fname, fname, length); // args args->begin_argv = args->buf + 1 + strlen(fname); args->endp = args->begin_argv; for(i = 0; argv[i] != NULL; ++i) { length = 1 + strlen(argv[i]); memcpy(args->endp, argv[i], length); args->stringspace -= length; args->endp += length; (args->argc)++; } // envv args->begin_envv = args->endp; args->endp = args->begin_envv; for(i = 0; envv[i] != NULL; ++i) { length = 1 + strlen(envv[i]); memcpy(args->endp, envv[i], length); args->stringspace -= length; args->endp += length; (args->envc)++; } return 0; } static int runapp_init(void) { int error; char *argv[] = { "/usr/bin/logger", "it works", NULL }; char *envv[] = { NULL }; struct image_args args; error = make_args(&args, argv[0], argv, envv); if(error != 0) { return error; } error = kern_execve(curthread, &args, NULL); if(error != 0) { if(DEBUG) { printf("kern_execve() failed\n"); uprintf("kern_execve() failed\n"); } return error; } return 0; } static int event_handler(struct module *module, int event, void *arg) { switch(event) { case MOD_LOAD: printf("Hello, World! I'm loaded!\n"); uprintf("Hello, World! I'm loaded!\n"); return runapp_init(); case MOD_UNLOAD: case MOD_QUIESCE: printf("Bye Bye Cruel World!\n"); printf("Bye Bye Cruel World!\n"); return 0; } return EOPNOTSUPP; } static moduledata_t runapp_conf = { "runapp", /* module name */ event_handler, /* event handler */ NULL /* extra data */ }; DECLARE_MODULE(runapp, runapp_conf, SI_SUB_DRIVERS, SI_ORDER_ANY); --bcaec51b1b6f215daa04e276f0ae--
Want to link to this message? Use this URL: <https://mail-archive.FreeBSD.org/cgi/mid.cgi?CAHORHL=yF3V2--HxuahNDQjYRwThKZY0_gUXk0SsZA8gu8FDAQ>