Error with call_usermodehelper API
diamondback
kapilanand2 at gmail.com
Mon Dec 30 18:11:04 EST 2013
I am having a problem with the use of call_usermodehelper API. I am using
this API inside Kernel jprobes module to trap start_thread function. This
API works well if I provide UMH_WAIT_EXEC as wait parameter, but it fails to
load the process when UMH_WAIT_PROC is passed as parameter.
Specifically, the following code works properly.
#include <linux/kernel.h>
#include <linux/module.h>
#include <linux/sched.h>
#include <linux/kprobes.h>
#include <linux/kallsyms.h>
#include <linux/ptrace.h>
#include <linux/kmod.h>
#include <linux/syscalls.h>
#include <linux/delay.h>
static struct jprobe start_thread_jprobe;
static asmlinkage int kp_start_thread(struct pt_regs* regs,
unsigned long new_ip,unsigned long new_sp){
int retval;
char * envp[] = { NULL };
char* argv[]={"/bin/ls",NULL};
//Only modifying this for a process named test1
if(strcmp(current->comm,"test1")==0){
retval=call_usermodehelper(argv[0], argv, envp, UMH_WAIT_EXEC);
if(retval<0){
printk("Failed in starting! %d\n",retval);
}
else {
printk("Succeded in starting %d\n",retval);
}
}
jprobe_return();
/*NOTREACHED*/
return (0);
}
int init_module(void)
{
int ret;
start_thread_jprobe.entry = (kprobe_opcode_t *)kp_start_thread;
start_thread_jprobe.kp.addr = (kprobe_opcode_t *)
kallsyms_lookup_name("start_thread");
if (!start_thread_jprobe.kp.addr) {
printk("unable to lookup symbol\n");
return (-1);
}
if ((ret = register_jprobe(&start_thread_jprobe)) <0) {
printk("register_jprobe failed, returned %d\n", ret);
return (-1);
}
return (0);
}
But if I update the call to call_usemodehelper as follows.
retval=call_usermodehelper(argv[0], argv, envp, UMH_WAIT_PROC);
The above call fails to load *ls* using this API. It gives an error number
-14 (EFAULT).
A simple test is as follows:
test1.c
#include <stdio.h>
int main(){
printf("This is test1\n");
return 0;
}
Makefile for module:
obj-m := kp-start-thread.o
KDIR := /lib/modules/$(shell uname -r)/build
PWD := $(shell pwd)
default:
$(MAKE) -C $(KDIR) SUBDIRS=$(PWD) modules
clean:
rm -f *.mod.c *.ko *.o
Test:
gcc test1.c -o test1
make
sudo insmod ./kp-start-thread.ko
./test1
dmesg ---> Will demonstrate success message with EXEC and failure
with WAIT.
More information about the Kernelnewbies
mailing list