1 /* modprobe.c: add or remove a module from the kernel, intelligently.
2 Copyright (C) 2001 Rusty Russell.
3 Copyright (C) 2002, 2003 Rusty Russell, IBM Corporation.
5 This program is free software; you can redistribute it and/or modify
6 it under the terms of the GNU General Public License as published by
7 the Free Software Foundation; either version 2 of the License, or
8 (at your option) any later version.
10 This program is distributed in the hope that it will be useful,
11 but WITHOUT ANY WARRANTY; without even the implied warranty of
12 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
13 GNU General Public License for more details.
15 You should have received a copy of the GNU General Public License
16 along with this program; if not, write to the Free Software
17 Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
19 #define _GNU_SOURCE /* asprintf */
21 #include <sys/utsname.h>
22 #include <sys/types.h>
38 #include <asm/unistd.h>
42 #define streq(a,b) (strcmp((a),(b)) == 0)
43 #define ARRAY_SIZE(x) (sizeof(x) / sizeof((x)[0]))
45 #include "zlibsupport.h"
49 #include "config_filter.h"
53 int use_binary_indexes
= 1; /* default to enabled. */
55 extern long init_module(void *, unsigned long, const char *);
56 extern long delete_module(const char *, unsigned int);
59 struct list_head list
;
65 #define MODULE_DIR "/lib/modules"
68 typedef void (*errfn_t
)(const char *fmt
, ...);
70 static void grammar(const char *cmd
, const char *filename
, unsigned int line
)
72 warn("%s line %u: ignoring bad line starting with '%s'\n",
76 static void print_usage(const char *progname
)
79 "Usage: %s [-v] [-V] [-C config-file] [-d <dirname> ] [-n] [-i] [-q] [-b] [-o <modname>] [ --dump-modversions ] <modname> [parameters...]\n"
80 "%s -r [-n] [-i] [-v] <modulename> ...\n"
81 "%s -l -t <dirname> [ -a <modulename> ...]\n",
82 progname
, progname
, progname
);
86 static char *getline_wrapped(FILE *file
, unsigned int *linenum
)
90 char *buf
= NOFAIL(malloc(size
));
92 int ch
= getc_unlocked(file
);
100 /* else fall through */
106 buf
= NOFAIL(realloc(buf
, size
+ 1));
111 ch
= getc_unlocked(file
);
118 /* else fall through */
125 buf
= NOFAIL(realloc(buf
, size
));
131 static struct module
*find_module(const char *filename
, struct list_head
*list
)
135 list_for_each_entry(i
, list
, list
) {
136 if (strcmp(i
->filename
, filename
) == 0)
142 /* Convert filename to the module name. Works if filename == modname, too. */
143 static void filename2modname(char *modname
, const char *filename
)
145 const char *afterslash
;
148 afterslash
= strrchr(filename
, '/');
150 afterslash
= filename
;
154 /* Convert to underscores, stop at first . */
155 for (i
= 0; afterslash
[i
] && afterslash
[i
] != '.'; i
++) {
156 if (afterslash
[i
] == '-')
159 modname
[i
] = afterslash
[i
];
164 static int lock_file(const char *filename
)
166 int fd
= open(filename
, O_RDWR
, 0);
170 lock
.l_type
= F_WRLCK
;
171 lock
.l_whence
= SEEK_SET
;
174 fcntl(fd
, F_SETLKW
, &lock
);
176 /* Read-only filesystem? There goes locking... */
177 fd
= open(filename
, O_RDONLY
, 0);
181 static void unlock_file(int fd
)
183 /* Valgrind is picky... */
187 static void add_module(char *filename
, int namelen
, struct list_head
*list
)
191 /* If it's a duplicate: move it to the end, so it gets
192 inserted where it is *first* required. */
193 mod
= find_module(filename
, list
);
195 list_del(&mod
->list
);
197 /* No match. Create a new module. */
198 mod
= NOFAIL(malloc(sizeof(struct module
) + namelen
+ 1));
199 memcpy(mod
->filename
, filename
, namelen
);
200 mod
->filename
[namelen
] = '\0';
201 mod
->modname
= NOFAIL(malloc(namelen
+ 1));
202 filename2modname(mod
->modname
, mod
->filename
);
205 list_add_tail(&mod
->list
, list
);
208 /* Compare len chars of a to b, with _ and - equivalent. */
209 static int modname_equal(const char *a
, const char *b
, unsigned int len
)
213 if (strlen(b
) != len
)
216 for (i
= 0; i
< len
; i
++) {
217 if ((a
[i
] == '_' || a
[i
] == '-')
218 && (b
[i
] == '_' || b
[i
] == '-'))
226 /* Fills in list of modules if this is the line we want. */
227 static int add_modules_dep_line(char *line
,
229 struct list_head
*list
,
234 char *modname
, *fullpath
;
236 /* Ignore lines without : or which start with a # */
237 ptr
= strchr(line
, ':');
238 if (ptr
== NULL
|| line
[strspn(line
, "\t ")] == '#')
241 /* Is this the module we are looking for? */
243 if (strrchr(line
, '/'))
244 modname
= strrchr(line
, '/') + 1;
248 len
= strlen(modname
);
249 if (strchr(modname
, '.'))
250 len
= strchr(modname
, '.') - modname
;
251 if (!modname_equal(modname
, name
, len
))
254 /* Create the list. */
255 if ('/' == line
[0]) { /* old style deps - absolute path specified */
256 add_module(line
, ptr
- line
, list
);
258 nofail_asprintf(&fullpath
, "%s/%s", dirname
, line
);
259 add_module(fullpath
, strlen(dirname
)+1+(ptr
- line
), list
);
266 ptr
+= strspn(ptr
, " \t");
270 ptr
+= strcspn(ptr
, " \t");
271 if ('/' == dep_start
[0]) { /* old style deps */
272 add_module(dep_start
, ptr
- dep_start
, list
);
274 nofail_asprintf(&fullpath
, "%s/%s", dirname
, dep_start
);
276 strlen(dirname
)+1+(ptr
- dep_start
), list
);
283 static int read_depends_bin(const char *dirname
,
284 const char *start_name
,
285 struct list_head
*list
)
287 char *modules_dep_name
;
289 struct index_file
*modules_dep
;
291 nofail_asprintf(&modules_dep_name
, "%s/%s", dirname
, "modules.dep.bin");
292 modules_dep
= index_file_open(modules_dep_name
);
294 free(modules_dep_name
);
298 line
= index_search(modules_dep
, start_name
);
300 /* Value is standard dependency line format */
301 if (!add_modules_dep_line(line
, start_name
, list
, dirname
))
302 fatal("Module index is inconsistent\n");
306 index_file_close(modules_dep
);
307 free(modules_dep_name
);
312 static void read_depends(const char *dirname
,
313 const char *start_name
,
314 struct list_head
*list
)
316 char *modules_dep_name
;
321 if (read_depends_bin(dirname
, start_name
, list
))
324 nofail_asprintf(&modules_dep_name
, "%s/%s", dirname
, "modules.dep");
325 modules_dep
= fopen(modules_dep_name
, "r");
327 fatal("Could not load %s: %s\n",
328 modules_dep_name
, strerror(errno
));
330 /* Stop at first line, as we can have duplicates (eg. symlinks
332 while (!done
&& (line
= getline_wrapped(modules_dep
, NULL
)) != NULL
) {
333 done
= add_modules_dep_line(line
, start_name
, list
, dirname
);
337 free(modules_dep_name
);
340 /* We use error numbers in a loose translation... */
341 static const char *insert_moderror(int err
)
345 return "Invalid module format";
347 return "Unknown symbol in module, or unknown parameter (see dmesg)";
349 return "Kernel does not have module support";
351 return strerror(err
);
355 static const char *remove_moderror(int err
)
359 return "No such module";
361 return "Kernel does not have module unloading support";
363 return strerror(err
);
367 static void replace_modname(struct module
*module
,
368 void *mem
, unsigned long len
,
369 const char *oldname
, const char *newname
)
373 /* 64 - sizeof(unsigned long) - 1 */
374 if (strlen(newname
) > 55)
375 fatal("New name %s is too long\n", newname
);
377 /* Find where it is in the module structure. Don't assume layout! */
378 for (p
= mem
; p
< (char *)mem
+ len
- strlen(oldname
); p
++) {
379 if (memcmp(p
, oldname
, strlen(oldname
)) == 0) {
385 warn("Could not find old name in %s to replace!\n", module
->filename
);
388 static void *get_section32(void *file
,
391 unsigned long *secsize
)
393 Elf32_Ehdr
*hdr
= file
;
394 Elf32_Shdr
*sechdrs
= file
+ hdr
->e_shoff
;
395 const char *secnames
;
399 if (size
< sizeof(*hdr
))
401 if (size
< hdr
->e_shoff
+ hdr
->e_shnum
* sizeof(sechdrs
[0]))
403 if (size
< sechdrs
[hdr
->e_shstrndx
].sh_offset
)
406 secnames
= file
+ sechdrs
[hdr
->e_shstrndx
].sh_offset
;
407 for (i
= 1; i
< hdr
->e_shnum
; i
++)
408 if (strcmp(secnames
+ sechdrs
[i
].sh_name
, name
) == 0) {
409 *secsize
= sechdrs
[i
].sh_size
;
410 return file
+ sechdrs
[i
].sh_offset
;
415 static void *get_section64(void *file
,
418 unsigned long *secsize
)
420 Elf64_Ehdr
*hdr
= file
;
421 Elf64_Shdr
*sechdrs
= file
+ hdr
->e_shoff
;
422 const char *secnames
;
426 if (size
< sizeof(*hdr
))
428 if (size
< hdr
->e_shoff
+ hdr
->e_shnum
* sizeof(sechdrs
[0]))
430 if (size
< sechdrs
[hdr
->e_shstrndx
].sh_offset
)
433 secnames
= file
+ sechdrs
[hdr
->e_shstrndx
].sh_offset
;
434 for (i
= 1; i
< hdr
->e_shnum
; i
++)
435 if (strcmp(secnames
+ sechdrs
[i
].sh_name
, name
) == 0) {
436 *secsize
= sechdrs
[i
].sh_size
;
437 return file
+ sechdrs
[i
].sh_offset
;
442 static int elf_ident(void *mod
, unsigned long size
)
444 /* "\177ELF" <byte> where byte = 001 for 32-bit, 002 for 64 */
447 if (size
< EI_CLASS
|| memcmp(mod
, ELFMAG
, SELFMAG
) != 0)
449 return ident
[EI_CLASS
];
452 static void *get_section(void *file
,
455 unsigned long *secsize
)
457 switch (elf_ident(file
, size
)) {
459 return get_section32(file
, size
, name
, secsize
);
461 return get_section64(file
, size
, name
, secsize
);
467 static void rename_module(struct module
*module
,
473 unsigned long modstruct_len
;
476 modstruct
= get_section(mod
, len
, ".gnu.linkonce.this_module",
480 modstruct
= get_section(mod
, len
, "__module", &modstruct_len
);
482 warn("Could not find module name to change in %s\n",
485 replace_modname(module
, modstruct
, modstruct_len
,
486 module
->modname
, newname
);
489 /* Kernel told to ignore these sections if SHF_ALLOC not set. */
490 static void invalidate_section32(void *mod
, const char *secname
)
492 Elf32_Ehdr
*hdr
= mod
;
493 Elf32_Shdr
*sechdrs
= mod
+ hdr
->e_shoff
;
494 const char *secnames
= mod
+ sechdrs
[hdr
->e_shstrndx
].sh_offset
;
497 for (i
= 1; i
< hdr
->e_shnum
; i
++)
498 if (strcmp(secnames
+sechdrs
[i
].sh_name
, secname
) == 0)
499 sechdrs
[i
].sh_flags
&= ~SHF_ALLOC
;
502 static void invalidate_section64(void *mod
, const char *secname
)
504 Elf64_Ehdr
*hdr
= mod
;
505 Elf64_Shdr
*sechdrs
= mod
+ hdr
->e_shoff
;
506 const char *secnames
= mod
+ sechdrs
[hdr
->e_shstrndx
].sh_offset
;
509 for (i
= 1; i
< hdr
->e_shnum
; i
++)
510 if (strcmp(secnames
+sechdrs
[i
].sh_name
, secname
) == 0)
511 sechdrs
[i
].sh_flags
&= ~(unsigned long long)SHF_ALLOC
;
514 static void strip_section(struct module
*module
,
519 switch (elf_ident(mod
, len
)) {
521 invalidate_section32(mod
, secname
);
524 invalidate_section64(mod
, secname
);
527 warn("Unknown module format in %s: not forcing version\n",
532 static const char *next_string(const char *string
, unsigned long *secsize
)
534 /* Skip non-zero chars */
537 if ((*secsize
)-- <= 1)
541 /* Skip any zero padding. */
544 if ((*secsize
)-- <= 1)
550 static void clear_magic(struct module
*module
, void *mod
, unsigned long len
)
553 unsigned long modlen
;
555 /* Old-style: __vermagic section */
556 strip_section(module
, mod
, len
, "__vermagic");
558 /* New-style: in .modinfo section */
559 for (p
= get_section(mod
, len
, ".modinfo", &modlen
);
561 p
= next_string(p
, &modlen
)) {
562 if (strncmp(p
, "vermagic=", strlen("vermagic=")) == 0) {
563 memset((char *)p
, 0, strlen(p
));
569 struct module_options
571 struct module_options
*next
;
576 struct module_command
578 struct module_command
*next
;
585 struct module_alias
*next
;
589 struct module_blacklist
591 struct module_blacklist
*next
;
595 /* Link in a new option line from the config file. */
596 static struct module_options
*
597 add_options(const char *modname
,
599 struct module_options
*options
)
601 struct module_options
*new;
604 new = NOFAIL(malloc(sizeof(*new)));
605 new->modulename
= NOFAIL(strdup(modname
));
606 new->options
= NOFAIL(strdup(option
));
607 /* We can handle tabs, kernel can't. */
608 for (tab
= strchr(new->options
, '\t'); tab
; tab
= strchr(tab
, '\t'))
614 /* Link in a new install line from the config file. */
615 static struct module_command
*
616 add_command(const char *modname
,
618 struct module_command
*commands
)
620 struct module_command
*new;
622 new = NOFAIL(malloc(sizeof(*new)));
623 new->modulename
= NOFAIL(strdup(modname
));
624 new->command
= NOFAIL(strdup(command
));
625 new->next
= commands
;
629 /* Link in a new alias line from the config file. */
630 static struct module_alias
*
631 add_alias(const char *modname
, struct module_alias
*aliases
)
633 struct module_alias
*new;
635 new = NOFAIL(malloc(sizeof(*new)));
636 new->module
= NOFAIL(strdup(modname
));
641 /* Link in a new blacklist line from the config file. */
642 static struct module_blacklist
*
643 add_blacklist(const char *modname
, struct module_blacklist
*blacklist
)
645 struct module_blacklist
*new;
647 new = NOFAIL(malloc(sizeof(*new)));
648 new->modulename
= NOFAIL(strdup(modname
));
649 new->next
= blacklist
;
653 /* Find blacklist commands if any. */
655 find_blacklist(const char *modname
, const struct module_blacklist
*blacklist
)
658 if (strcmp(blacklist
->modulename
, modname
) == 0)
660 blacklist
= blacklist
->next
;
665 /* return a new alias list, with backlisted elems filtered out */
666 static struct module_alias
*
667 apply_blacklist(const struct module_alias
*aliases
,
668 const struct module_blacklist
*blacklist
)
670 struct module_alias
*result
= NULL
;
672 char *modname
= aliases
->module
;
673 if (!find_blacklist(modname
, blacklist
))
674 result
= add_alias(modname
, result
);
675 aliases
= aliases
->next
;
680 /* Find install commands if any. */
681 static const char *find_command(const char *modname
,
682 const struct module_command
*commands
)
685 if (fnmatch(commands
->modulename
, modname
, 0) == 0)
686 return commands
->command
;
687 commands
= commands
->next
;
692 static char *append_option(char *options
, const char *newoption
)
694 options
= NOFAIL(realloc(options
, strlen(options
) + 1
695 + strlen(newoption
) + 1));
696 if (strlen(options
)) strcat(options
, " ");
697 strcat(options
, newoption
);
701 static char *prepend_option(char *options
, const char *newoption
)
704 l1
= strlen(options
);
705 l2
= strlen(newoption
);
706 /* the resulting string will look like
707 * newoption + ' ' + options + '\0' */
709 options
= NOFAIL(realloc(options
, l2
+ 1 + l1
+ 1));
710 memmove(options
+ l2
+ 1, options
, l1
+ 1);
712 memcpy(options
, newoption
, l2
);
714 options
= NOFAIL(realloc(options
, l2
+ 1));
715 memcpy(options
, newoption
, l2
);
722 static char *add_extra_options(const char *modname
,
724 const struct module_options
*options
)
727 if (strcmp(options
->modulename
, modname
) == 0)
728 optstring
= prepend_option(optstring
, options
->options
);
729 options
= options
->next
;
734 /* Read sysfs attribute into a buffer.
735 * returns: 1 = ok, 0 = attribute missing,
736 * -1 = file error (or empty file, but we don't care).
738 static int read_attribute(const char *filename
, char *buf
, size_t buflen
)
743 file
= fopen(filename
, "r");
745 return (errno
== ENOENT
) ? 0 : -1;
746 s
= fgets(buf
, buflen
, file
);
749 return (s
== NULL
) ? -1 : 1;
752 /* Is module in /sys/module? If so, fill in usecount if not NULL.
753 0 means no, 1 means yes, -1 means unknown.
755 static int module_in_kernel(const char *modname
, unsigned int *usecount
)
761 const int ATTR_LEN
= 16;
764 /* Check sysfs is mounted */
765 if (stat("/sys/module", &finfo
) < 0)
769 nofail_asprintf(&name
, "/sys/module/%s", modname
);
770 ret
= stat(name
, &finfo
);
773 return (errno
== ENOENT
) ? 0 : -1; /* Not found or unknown. */
775 /* Wait for the existing module to either go live or disappear. */
776 nofail_asprintf(&name
, "/sys/module/%s/initstate", modname
);
778 ret
= read_attribute(name
, attr
, ATTR_LEN
);
779 if (ret
!= 1 || streq(attr
, "live\n"))
789 /* Get reference count, if it exists. */
790 if (usecount
!= NULL
) {
791 nofail_asprintf(&name
, "/sys/module/%s/refcnt", modname
);
792 ret
= read_attribute(name
, attr
, ATTR_LEN
);
795 *usecount
= atoi(attr
);
801 /* If we don't flush, then child processes print before we do */
802 static void verbose_printf(int verbose
, const char *fmt
, ...)
807 va_start(arglist
, fmt
);
808 vprintf(fmt
, arglist
);
814 /* Do an install/remove command: replace $CMDLINE_OPTS if it's specified. */
815 static void do_command(const char *modname
,
817 int verbose
, int dry_run
,
820 const char *cmdline_opts
)
823 char *p
, *replaced_cmd
= NOFAIL(strdup(command
));
825 while ((p
= strstr(replaced_cmd
, "$CMDLINE_OPTS")) != NULL
) {
827 nofail_asprintf(&new, "%.*s%s%s",
828 (int)(p
- replaced_cmd
), replaced_cmd
, cmdline_opts
,
829 p
+ strlen("$CMDLINE_OPTS"));
834 verbose_printf(verbose
, "%s %s\n", type
, replaced_cmd
);
838 setenv("MODPROBE_MODULE", modname
, 1);
839 ret
= system(replaced_cmd
);
840 if (ret
== -1 || WEXITSTATUS(ret
))
841 error("Error running %s command for %s\n", type
, modname
);
845 /* Actually do the insert. Frees second arg. */
846 static void insmod(struct list_head
*list
,
853 const struct module_options
*options
,
854 const struct module_command
*commands
,
858 int strip_modversion
,
859 const char *cmdline_opts
)
865 struct module
*mod
= list_entry(list
->next
, struct module
, list
);
867 /* Take us off the list. */
868 list_del(&mod
->list
);
870 /* Do things we (or parent) depend on first, but don't die if
872 if (!list_empty(list
)) {
873 insmod(list
, NOFAIL(strdup("")), NULL
, 0, warn
,
874 dry_run
, verbose
, options
, commands
, 0, ignore_proc
,
875 strip_vermagic
, strip_modversion
, "");
878 /* Lock before we look, in case it's initializing. */
879 fd
= lock_file(mod
->filename
);
881 error("Could not open '%s': %s\n",
882 mod
->filename
, strerror(errno
));
886 /* Don't do ANYTHING if already in kernel. */
888 && module_in_kernel(newname
?: mod
->modname
, NULL
) == 1) {
890 error("Module %s already in kernel.\n",
891 newname
?: mod
->modname
);
895 command
= find_command(mod
->modname
, commands
);
896 if (command
&& !ignore_commands
) {
897 /* It might recurse: unlock. */
899 do_command(mod
->modname
, command
, verbose
, dry_run
, error
,
900 "install", cmdline_opts
);
904 map
= grab_fd(fd
, &len
);
906 error("Could not read '%s': %s\n",
907 mod
->filename
, strerror(errno
));
913 rename_module(mod
, map
, len
, newname
);
915 if (strip_modversion
)
916 strip_section(mod
, map
, len
, "__versions");
918 clear_magic(mod
, map
, len
);
920 /* Config file might have given more options */
921 optstring
= add_extra_options(mod
->modname
, optstring
, options
);
923 verbose_printf(verbose
, "insmod %s %s\n", mod
->filename
, optstring
);
928 ret
= init_module(map
, len
, optstring
);
930 if (errno
== EEXIST
) {
932 error("Module %s already in kernel.\n",
933 newname
?: mod
->modname
);
936 /* don't warn noisely if we're loading multiple aliases. */
937 /* one of the aliases may try to use hardware we don't have. */
938 if ((error
!= warn
) || (verbose
))
939 error("Error inserting %s (%s): %s\n",
940 mod
->modname
, mod
->filename
,
941 insert_moderror(errno
));
944 release_file(map
, len
);
952 /* Do recursive removal. */
953 static void rmmod(struct list_head
*list
,
959 struct module_command
*commands
,
962 const char *cmdline_opts
,
966 unsigned int usecount
= 0;
968 struct module
*mod
= list_entry(list
->next
, struct module
, list
);
970 /* Take first one off the list. */
971 list_del(&mod
->list
);
973 /* Ignore failure; it's best effort here. */
974 lock
= lock_file(mod
->filename
);
979 /* Even if renamed, find commands to orig. name. */
980 command
= find_command(mod
->modname
, commands
);
981 if (command
&& !ignore_commands
) {
982 /* It might recurse: unlock. */
984 do_command(mod
->modname
, command
, verbose
, dry_run
, error
,
985 "remove", cmdline_opts
);
986 goto remove_rest_no_unlock
;
989 if (module_in_kernel(name
, &usecount
) == 0)
990 goto nonexistent_module
;
994 error("Module %s is in use.\n", name
);
998 verbose_printf(verbose
, "rmmod %s\n", mod
->filename
);
1003 if (delete_module(name
, O_EXCL
) != 0) {
1004 if (errno
== ENOENT
)
1005 goto nonexistent_module
;
1006 error("Error removing %s (%s): %s\n",
1007 name
, mod
->filename
,
1008 remove_moderror(errno
));
1013 remove_rest_no_unlock
:
1014 /* Now do things we depend. */
1015 if (!list_empty(list
))
1016 rmmod(list
, NULL
, 0, warn
, dry_run
, verbose
, commands
,
1022 fatal("Module %s is not in kernel.\n", mod
->modname
);
1026 struct modver32_info
1029 char name
[64 - sizeof(uint32_t)];
1032 struct modver64_info
1035 char name
[64 - sizeof(uint64_t)];
1038 const char *skip_dot(const char *str
)
1040 /* For our purposes, .foo matches foo. PPC64 needs this. */
1041 if (str
&& str
[0] == '.')
1046 void dump_modversions(const char *filename
, errfn_t error
)
1048 unsigned long size
, secsize
;
1049 void *file
= grab_file(filename
, &size
);
1050 struct modver32_info
*info32
;
1051 struct modver64_info
*info64
;
1055 error("%s: %s\n", filename
, strerror(errno
));
1058 switch (elf_ident(file
, size
)) {
1060 info32
= get_section32(file
, size
, "__versions", &secsize
);
1062 return; /* Does not seem to be a kernel module */
1063 if (secsize
% sizeof(struct modver32_info
))
1064 error("Wrong section size in %s\n", filename
);
1065 for (n
= 0; n
< secsize
/ sizeof(struct modver32_info
); n
++)
1066 printf("0x%08lx\t%s\n", (unsigned long)
1067 info32
[n
].crc
, skip_dot(info32
[n
].name
));
1071 info64
= get_section64(file
, size
, "__versions", &secsize
);
1073 return; /* Does not seem to be a kernel module */
1074 if (secsize
% sizeof(struct modver64_info
))
1075 error("Wrong section size in %s\n", filename
);
1076 for (n
= 0; n
< secsize
/ sizeof(struct modver64_info
); n
++)
1077 printf("0x%08llx\t%s\n", (unsigned long long)
1078 info64
[n
].crc
, skip_dot(info64
[n
].name
));
1082 error("%s: ELF class not recognized\n", filename
);
1087 /* Does path contain directory(s) subpath? */
1088 static int type_matches(const char *path
, const char *subpath
)
1090 char *subpath_with_slashes
;
1093 nofail_asprintf(&subpath_with_slashes
, "/%s/", subpath
);
1095 ret
= (strstr(path
, subpath_with_slashes
) != NULL
);
1096 free(subpath_with_slashes
);
1100 /* Careful! Don't munge - in [ ] as per Debian Bug#350915 */
1101 static char *underscores(char *string
)
1106 for (i
= 0; string
[i
]; i
++) {
1107 switch (string
[i
]) {
1120 warn("Unmatched bracket in %s\n", string
);
1125 static int do_wildcard(const char *dirname
,
1127 const char *wildcard
)
1129 char *modules_dep_name
;
1133 /* Canonicalize wildcard */
1134 wcard
= strdup(wildcard
);
1137 nofail_asprintf(&modules_dep_name
, "%s/%s", dirname
, "modules.dep");
1138 modules_dep
= fopen(modules_dep_name
, "r");
1140 fatal("Could not load %s: %s\n",
1141 modules_dep_name
, strerror(errno
));
1143 while ((line
= getline_wrapped(modules_dep
, NULL
)) != NULL
) {
1146 /* Ignore lines without : or which start with a # */
1147 ptr
= strchr(line
, ':');
1148 if (ptr
== NULL
|| line
[strspn(line
, "\t ")] == '#')
1152 /* "type" must match complete directory component(s). */
1153 if (!type
|| type_matches(line
, type
)) {
1154 char modname
[strlen(line
)+1];
1156 filename2modname(modname
, line
);
1157 if (fnmatch(wcard
, modname
, 0) == 0)
1158 printf("%s\n", line
);
1164 free(modules_dep_name
);
1169 static char *strsep_skipspace(char **string
, char *delim
)
1173 *string
+= strspn(*string
, delim
);
1174 return strsep(string
, delim
);
1178 static int read_config(const char *filename
,
1182 struct module_options
**options
,
1183 struct module_command
**commands
,
1184 struct module_alias
**alias
,
1185 struct module_blacklist
**blacklist
);
1187 /* FIXME: Maybe should be extended to "alias a b [and|or c]...". --RR */
1188 static int read_config_file(const char *filename
,
1192 struct module_options
**options
,
1193 struct module_command
**commands
,
1194 struct module_alias
**aliases
,
1195 struct module_blacklist
**blacklist
)
1198 unsigned int linenum
= 0;
1201 cfile
= fopen(filename
, "r");
1205 while ((line
= getline_wrapped(cfile
, &linenum
)) != NULL
) {
1207 char *cmd
, *modname
;
1210 printf("%s\n", line
);
1212 cmd
= strsep_skipspace(&ptr
, "\t ");
1213 if (cmd
== NULL
|| cmd
[0] == '#' || cmd
[0] == '\0') {
1218 if (strcmp(cmd
, "alias") == 0) {
1220 = underscores(strsep_skipspace(&ptr
, "\t "));
1222 = underscores(strsep_skipspace(&ptr
, "\t "));
1224 if (!wildcard
|| !realname
)
1225 grammar(cmd
, filename
, linenum
);
1226 else if (fnmatch(wildcard
,name
,0) == 0)
1227 *aliases
= add_alias(realname
, *aliases
);
1228 } else if (strcmp(cmd
, "include") == 0) {
1229 struct module_alias
*newalias
= NULL
;
1232 newfilename
= strsep_skipspace(&ptr
, "\t ");
1234 grammar(cmd
, filename
, linenum
);
1236 if (!read_config(newfilename
, name
,
1237 dump_only
, removing
,
1238 options
, commands
, &newalias
,
1240 warn("Failed to open included"
1241 " config file %s: %s\n",
1242 newfilename
, strerror(errno
));
1244 /* Files included override aliases,
1245 etc that was already set ... */
1247 *aliases
= newalias
;
1249 } else if (strcmp(cmd
, "options") == 0) {
1250 modname
= strsep_skipspace(&ptr
, "\t ");
1251 if (!modname
|| !ptr
)
1252 grammar(cmd
, filename
, linenum
);
1254 ptr
+= strspn(ptr
, "\t ");
1255 *options
= add_options(underscores(modname
),
1258 } else if (strcmp(cmd
, "install") == 0) {
1259 modname
= strsep_skipspace(&ptr
, "\t ");
1260 if (!modname
|| !ptr
)
1261 grammar(cmd
, filename
, linenum
);
1262 else if (!removing
) {
1263 ptr
+= strspn(ptr
, "\t ");
1264 *commands
= add_command(underscores(modname
),
1267 } else if (strcmp(cmd
, "blacklist") == 0) {
1268 modname
= strsep_skipspace(&ptr
, "\t ");
1270 grammar(cmd
, filename
, linenum
);
1271 else if (!removing
) {
1272 *blacklist
= add_blacklist(underscores(modname
),
1275 } else if (strcmp(cmd
, "remove") == 0) {
1276 modname
= strsep_skipspace(&ptr
, "\t ");
1277 if (!modname
|| !ptr
)
1278 grammar(cmd
, filename
, linenum
);
1279 else if (removing
) {
1280 ptr
+= strspn(ptr
, "\t ");
1281 *commands
= add_command(underscores(modname
),
1284 } else if (strcmp(cmd
, "config") == 0) {
1285 char *tmp
= strsep_skipspace(&ptr
, "\t ");
1286 if (strcmp(tmp
, "binary_indexes") == 0) {
1287 tmp
= strsep_skipspace(&ptr
, "\t ");
1288 if (strcmp(tmp
, "yes") == 0)
1289 use_binary_indexes
= 1;
1290 if (strcmp(tmp
, "no") == 0)
1291 use_binary_indexes
= 0;
1294 grammar(cmd
, filename
, linenum
);
1302 /* Simple format, ignore lines starting with #, one command per line.
1303 Returns true or false. */
1304 static int read_config(const char *filename
,
1308 struct module_options
**options
,
1309 struct module_command
**commands
,
1310 struct module_alias
**aliases
,
1311 struct module_blacklist
**blacklist
)
1316 /* Reiser4 has file/directory duality: treat it as both. */
1317 dir
= opendir(filename
);
1320 while ((i
= readdir(dir
)) != NULL
) {
1321 if (!streq(i
->d_name
,".") && !streq(i
->d_name
,"..")
1322 && config_filter(i
->d_name
)) {
1323 char sub
[strlen(filename
) + 1
1324 + strlen(i
->d_name
) + 1];
1326 sprintf(sub
, "%s/%s", filename
, i
->d_name
);
1327 if (!read_config(sub
, name
,
1328 dump_only
, removing
, options
,
1329 commands
, aliases
, blacklist
))
1330 warn("Failed to open"
1331 " config file %s: %s\n",
1332 sub
, strerror(errno
));
1339 if (read_config_file(filename
, name
, dump_only
, removing
,
1340 options
, commands
, aliases
, blacklist
))
1346 /* Read binary index file containing aliases only */
1347 /* fallback to legacy aliases file as necessary */
1348 static int read_config_file_bin(const char *filename
,
1352 struct module_options
**options
,
1353 struct module_command
**commands
,
1354 struct module_alias
**aliases
,
1355 struct module_blacklist
**blacklist
)
1357 struct index_value
*realnames
;
1358 struct index_value
*realname
;
1360 struct index_file
*index
;
1362 nofail_asprintf(&binfile
, "%s.bin", filename
);
1363 index
= index_file_open(binfile
);
1367 return read_config_file(filename
, name
, dump_only
, removing
,
1368 options
, commands
, aliases
, blacklist
);
1372 index_dump(index
, stdout
, "alias ");
1374 index_file_close(index
);
1378 realnames
= index_searchwild(index
, name
);
1379 for (realname
= realnames
; realname
; realname
= realname
->next
)
1380 *aliases
= add_alias(realname
->value
, *aliases
);
1381 index_values_free(realnames
);
1384 index_file_close(index
);
1388 static const char *default_configs
[] =
1390 "/etc/modprobe.conf",
1394 static void read_toplevel_config(const char *filename
,
1398 struct module_options
**options
,
1399 struct module_command
**commands
,
1400 struct module_alias
**aliases
,
1401 struct module_blacklist
**blacklist
)
1406 if (!read_config(filename
, name
, dump_only
, removing
,
1407 options
, commands
, aliases
, blacklist
))
1408 fatal("Failed to open config file %s: %s\n",
1409 filename
, strerror(errno
));
1414 for (i
= 0; i
< ARRAY_SIZE(default_configs
); i
++) {
1415 read_config(default_configs
[i
], name
, dump_only
, removing
,
1416 options
, commands
, aliases
, blacklist
);
1420 /* Read possible module arguments from the kernel command line. */
1421 static int read_kcmdline(int dump_only
, struct module_options
**options
)
1424 unsigned int linenum
= 0;
1427 kcmdline
= fopen("/proc/cmdline", "r");
1431 while ((line
= getline_wrapped(kcmdline
, &linenum
)) != NULL
) {
1435 while ((arg
= strsep_skipspace(&ptr
, "\t ")) != NULL
) {
1436 char *sep
, *modname
, *opt
;
1438 sep
= strchr(arg
, '.');
1440 if (!strchr(sep
, '='))
1447 printf("options %s %s\n", modname
, opt
);
1449 *options
= add_options(underscores(modname
),
1460 static void add_to_env_var(const char *option
)
1464 if ((oldenv
= getenv("MODPROBE_OPTIONS")) != NULL
) {
1466 nofail_asprintf(&newenv
, "%s %s", oldenv
, option
);
1467 setenv("MODPROBE_OPTIONS", newenv
, 1);
1469 setenv("MODPROBE_OPTIONS", option
, 1);
1472 /* Prepend options from environment. */
1473 static char **merge_args(char *args
, char *argv
[], int *argc
)
1475 char *arg
, *argstring
;
1476 char **newargs
= NULL
;
1477 unsigned int i
, num_env
= 0;
1482 argstring
= NOFAIL(strdup(args
));
1483 for (arg
= strtok(argstring
, " "); arg
; arg
= strtok(NULL
, " ")) {
1485 newargs
= NOFAIL(realloc(newargs
,
1487 * (num_env
+ *argc
+ 1)));
1488 newargs
[num_env
] = arg
;
1491 /* Append commandline args */
1492 newargs
[0] = argv
[0];
1493 for (i
= 1; i
<= *argc
; i
++)
1494 newargs
[num_env
+i
] = argv
[i
];
1500 static char *gather_options(char *argv
[])
1502 char *optstring
= NOFAIL(strdup(""));
1504 /* Rest is module options */
1506 /* Quote value if it contains spaces. */
1507 unsigned int eq
= strcspn(*argv
, "=");
1509 if (strchr(*argv
+eq
, ' ') && !strchr(*argv
, '"')) {
1510 char quoted
[strlen(*argv
) + 3];
1512 sprintf(quoted
, "%s=\"%s\"", *argv
, *argv
+eq
+1);
1513 optstring
= append_option(optstring
, quoted
);
1515 optstring
= append_option(optstring
, *argv
);
1521 static void handle_module(const char *modname
,
1522 struct list_head
*todo_list
,
1523 const char *newname
,
1530 struct module_options
*modoptions
,
1531 struct module_command
*commands
,
1532 int ignore_commands
,
1535 int strip_modversion
,
1537 const char *cmdline_opts
,
1540 if (list_empty(todo_list
)) {
1541 const char *command
;
1543 /* The dependencies have to be real modules, but
1544 handle case where the first is completely bogus. */
1545 command
= find_command(modname
, commands
);
1546 if (command
&& !ignore_commands
) {
1547 do_command(modname
, command
, verbose
, dry_run
, error
,
1548 remove
? "remove":"install", cmdline_opts
);
1554 error("Module %s not found.\n", modname
);
1559 rmmod(todo_list
, newname
, first_time
, error
, dry_run
, verbose
,
1560 commands
, ignore_commands
, 0, cmdline_opts
, flags
);
1562 insmod(todo_list
, NOFAIL(strdup(options
)), newname
,
1563 first_time
, error
, dry_run
, verbose
, modoptions
,
1564 commands
, ignore_commands
, ignore_proc
, strip_vermagic
,
1565 strip_modversion
, cmdline_opts
);
1568 static struct option options
[] = { { "verbose", 0, NULL
, 'v' },
1569 { "version", 0, NULL
, 'V' },
1570 { "config", 1, NULL
, 'C' },
1571 { "name", 1, NULL
, 'o' },
1572 { "remove", 0, NULL
, 'r' },
1573 { "wait", 0, NULL
, 'w' },
1574 { "showconfig", 0, NULL
, 'c' },
1575 { "autoclean", 0, NULL
, 'k' },
1576 { "quiet", 0, NULL
, 'q' },
1577 { "show", 0, NULL
, 'n' },
1578 { "dry-run", 0, NULL
, 'n' },
1579 { "syslog", 0, NULL
, 's' },
1580 { "type", 1, NULL
, 't' },
1581 { "list", 0, NULL
, 'l' },
1582 { "all", 0, NULL
, 'a' },
1583 { "ignore-install", 0, NULL
, 'i' },
1584 { "ignore-remove", 0, NULL
, 'i' },
1585 { "force", 0, NULL
, 'f' },
1586 { "force-vermagic", 0, NULL
, 1 },
1587 { "force-modversion", 0, NULL
, 2 },
1588 { "set-version", 1, NULL
, 'S' },
1589 { "show-depends", 0, NULL
, 'D' },
1590 { "dirname", 1, NULL
, 'd' },
1591 { "first-time", 0, NULL
, 3 },
1592 { "dump-modversions", 0, NULL
, 4 },
1593 { "use-blacklist", 0, NULL
, 'b' },
1594 { NULL
, 0, NULL
, 0 } };
1596 int main(int argc
, char *argv
[])
1599 struct stat statbuf
;
1605 int unknown_silent
= 0;
1608 int ignore_commands
= 0;
1609 int strip_vermagic
= 0;
1610 int strip_modversion
= 0;
1611 int ignore_proc
= 0;
1613 int dump_modver
= 0;
1614 int use_blacklist
= 0;
1615 unsigned int i
, num_modules
;
1617 const char *config
= NULL
;
1618 char *dirname
= NULL
;
1619 char *optstring
= NULL
;
1620 char *newname
= NULL
;
1621 char *aliasfilename
, *symfilename
;
1622 errfn_t error
= fatal
;
1623 int flags
= O_NONBLOCK
|O_EXCL
;
1625 /* Prepend options from environment. */
1626 argv
= merge_args(getenv("MODPROBE_OPTIONS"), argv
, &argc
);
1629 while ((opt
= getopt_long(argc
, argv
, "vVC:o:rknqQsclt:aifbwd:", options
, NULL
)) != -1){
1632 add_to_env_var("-v");
1636 puts(PACKAGE
" version " VERSION
);
1639 strncpy(buf
.release
, optarg
, sizeof(buf
.release
));
1640 buf
.release
[sizeof(buf
.release
)-1] = '\0';
1644 add_to_env_var("-C");
1645 add_to_env_var(config
);
1649 add_to_env_var("-q");
1655 add_to_env_var("-D");
1677 /* FIXME: This should actually do something */
1683 add_to_env_var("-s");
1687 ignore_commands
= 1;
1691 strip_modversion
= 1;
1697 flags
&= ~O_NONBLOCK
;
1700 nofail_asprintf(&dirname
, "%s/%s/%s", optarg
,
1701 MODULE_DIR
, buf
.release
);
1707 strip_modversion
= 1;
1716 print_usage(argv
[0]);
1720 /* If stderr not open, go to syslog */
1721 if (logging
|| fstat(STDERR_FILENO
, &statbuf
) != 0) {
1722 openlog("modprobe", LOG_CONS
, LOG_DAEMON
);
1726 if (argc
< optind
+ 1 && !dump_only
&& !list_only
&& !remove
)
1727 print_usage(argv
[0]);
1730 nofail_asprintf(&dirname
, "%s/%s", MODULE_DIR
, buf
.release
);
1731 nofail_asprintf(&aliasfilename
, "%s/modules.alias", dirname
);
1732 nofail_asprintf(&symfilename
, "%s/modules.symbols", dirname
);
1734 /* Old-style -t xxx wildcard? Only with -l. */
1736 if (optind
+1 < argc
)
1737 fatal("Can't have multiple wildcards\n");
1738 /* fprintf(stderr, "man find\n"); return 1; */
1739 return do_wildcard(dirname
, type
, argv
[optind
]?:"*");
1742 fatal("-t only supported with -l");
1745 struct module_command
*commands
= NULL
;
1746 struct module_options
*modoptions
= NULL
;
1747 struct module_alias
*aliases
= NULL
;
1748 struct module_blacklist
*blacklist
= NULL
;
1750 read_toplevel_config(config
, "", 1, 0,
1751 &modoptions
, &commands
, &aliases
, &blacklist
);
1752 read_kcmdline(1, &modoptions
);
1753 if (use_binary_indexes
) {
1754 read_config_file_bin(aliasfilename
, "", 1, 0,
1755 &modoptions
, &commands
, &aliases
, &blacklist
);
1756 read_config_file_bin(symfilename
, "", 1, 0,
1757 &modoptions
, &commands
, &aliases
, &blacklist
);
1759 read_config(aliasfilename
, "", 1, 0,
1760 &modoptions
, &commands
, &aliases
, &blacklist
);
1761 read_config(symfilename
, "", 1, 0,
1762 &modoptions
, &commands
, &aliases
, &blacklist
);
1767 if (remove
|| all
) {
1768 num_modules
= argc
- optind
;
1769 optstring
= NOFAIL(strdup(""));
1772 optstring
= gather_options(argv
+optind
+1);
1775 /* num_modules is always 1 except for -r or -a. */
1776 for (i
= 0; i
< num_modules
; i
++) {
1777 struct module_command
*commands
= NULL
;
1778 struct module_options
*modoptions
= NULL
;
1779 struct module_alias
*aliases
= NULL
;
1780 struct module_blacklist
*blacklist
= NULL
;
1782 char *modulearg
= argv
[optind
+ i
];
1785 dump_modversions(modulearg
, error
);
1789 /* Convert name we are looking for */
1790 underscores(modulearg
);
1792 /* Returns the resolved alias, options */
1793 read_toplevel_config(config
, modulearg
, 0,
1794 remove
, &modoptions
, &commands
, &aliases
, &blacklist
);
1796 /* Read module options from kernel command line */
1797 read_kcmdline(0, &modoptions
);
1799 /* No luck? Try symbol names, if starts with symbol:. */
1801 && strncmp(modulearg
, "symbol:", strlen("symbol:")) == 0) {
1802 if (use_binary_indexes
)
1803 read_config_file_bin(symfilename
, modulearg
, 0,
1804 remove
, &modoptions
, &commands
,
1805 &aliases
, &blacklist
);
1807 read_config(symfilename
, modulearg
, 0,
1808 remove
, &modoptions
, &commands
,
1809 &aliases
, &blacklist
);
1812 if(!strchr(modulearg
, ':'))
1813 read_depends(dirname
, modulearg
, &list
);
1815 /* We only use canned aliases as last resort. */
1816 if (list_empty(&list
)
1817 && !find_command(modulearg
, commands
))
1819 if (use_binary_indexes
)
1820 read_config_file_bin(aliasfilename
,
1821 modulearg
, 0, remove
,
1822 &modoptions
, &commands
,
1823 &aliases
, &blacklist
);
1825 read_config(aliasfilename
,
1826 modulearg
, 0, remove
,
1827 &modoptions
, &commands
,
1828 &aliases
, &blacklist
);
1832 aliases
= apply_blacklist(aliases
, blacklist
);
1834 errfn_t err
= error
;
1836 /* More than one alias? Don't bail out on failure. */
1840 /* Add the options for this alias. */
1841 char *opts
= NOFAIL(strdup(optstring
));
1842 opts
= add_extra_options(modulearg
,
1845 read_depends(dirname
, aliases
->module
, &list
);
1846 handle_module(aliases
->module
, &list
, newname
,
1847 remove
, opts
, first_time
, err
,
1848 dry_run
, verbose
, modoptions
,
1849 commands
, ignore_commands
,
1850 ignore_proc
, strip_vermagic
,
1855 aliases
= aliases
->next
;
1856 INIT_LIST_HEAD(&list
);
1860 && find_blacklist(modulearg
, blacklist
))
1863 handle_module(modulearg
, &list
, newname
, remove
,
1864 optstring
, first_time
, error
, dry_run
,
1865 verbose
, modoptions
, commands
,
1866 ignore_commands
, ignore_proc
,
1867 strip_vermagic
, strip_modversion
,
1868 unknown_silent
, optstring
, flags
);
1875 free(aliasfilename
);