Import 2.1.116pre2
[davej-history.git] / kernel / kmod.c
blob1df9f4356c8f038adb88e6049b979c18d80625dc
1 /*
2 kmod, the new module loader (replaces kerneld)
3 Kirk Petersen
5 Reorganized not to be a daemon by Adam Richter, with guidance
6 from Greg Zornetzer.
8 Modified to avoid chroot and file sharing problems.
9 Mikael Pettersson
12 #define __KERNEL_SYSCALLS__
14 #include <linux/sched.h>
15 #include <linux/types.h>
16 #include <linux/unistd.h>
17 #include <linux/smp_lock.h>
19 #include <asm/uaccess.h>
22 modprobe_path is set via /proc/sys.
24 char modprobe_path[256] = "/sbin/modprobe";
25 static char * envp[] = { "HOME=/", "TERM=linux", "PATH=/sbin:/usr/sbin:/bin:/usr/bin", NULL };
28 exec_modprobe is spawned from a kernel-mode user process,
29 then changes its state to behave _as_if_ it was spawned
30 from the kernel's init process
31 (ppid and {e,}gid are not adjusted, but that shouldn't
32 be a problem since we trust modprobe)
34 #define task_init task[smp_num_cpus]
36 static inline void
37 use_init_file_context(void)
39 lock_kernel();
41 /* don't use the user's root, use init's root instead */
42 exit_fs(current); /* current->fs->count--; */
43 current->fs = task_init->fs;
44 current->fs->count++;
46 unlock_kernel();
49 static int exec_modprobe(void * module_name)
51 char *argv[] = { modprobe_path, "-s", "-k", (char*)module_name, NULL};
52 int i;
54 use_init_file_context();
56 /* Prevent parent user process from sending signals to child.
57 Otherwise, if the modprobe program does not exist, it might
58 be possible to get a user defined signal handler to execute
59 as the super user right after the execve fails if you time
60 the signal just right.
62 spin_lock_irq(&current->sigmask_lock);
63 flush_signals(current);
64 flush_signal_handlers(current);
65 spin_unlock_irq(&current->sigmask_lock);
67 for (i = 0; i < current->files->max_fds; i++ ) {
68 if (current->files->fd[i]) close(i);
71 /* Drop the "current user" thing */
72 free_uid(current);
74 /* Give kmod all privileges.. */
75 current->uid = current->euid = current->fsuid = 0;
76 cap_set_full(current->cap_inheritable);
77 cap_set_full(current->cap_effective);
79 /* Allow execve args to be in kernel space. */
80 set_fs(KERNEL_DS);
82 /* Go, go, go... */
83 if (execve(modprobe_path, argv, envp) < 0) {
84 printk(KERN_ERR
85 "kmod: failed to exec %s -s -k %s, errno = %d\n",
86 modprobe_path, (char*) module_name, errno);
87 return -errno;
89 return 0;
93 request_module: the function that everyone calls when they need
94 a module.
96 int request_module(const char * module_name)
98 int pid;
99 int waitpid_result;
101 /* Don't allow request_module() before the root fs is mounted! */
102 if ( ! current->fs->root ) {
103 printk(KERN_ERR "request_module[%s]: Root fs not mounted\n",
104 module_name);
105 return -EPERM;
108 pid = kernel_thread(exec_modprobe, (void*) module_name, CLONE_FS);
109 if (pid < 0) {
110 printk(KERN_ERR "kmod: fork failed, errno %d\n", -pid);
111 return pid;
113 waitpid_result = waitpid(pid, NULL, __WCLONE);
114 if (waitpid_result != pid) {
115 printk (KERN_ERR "kmod: waitpid(%d,NULL,0) failed, returning %d.\n",
116 pid, waitpid_result);
118 return 0;