1 /* vi: set sw=4 ts=4: */
3 * Mini insmod implementation for busybox
5 * Copyright (C) 1999,2000 by Lineo, inc.
6 * Written by Erik Andersen <andersen@lineo.com>
7 * and Ron Alder <alder@lineo.com>
9 * Modified by Bryan Rittmeyer <bryan@ixiacom.com> to support SH4
10 * and (theoretically) SH3. I have only tested SH4 in little endian mode.
12 * Modified by Alcove, Julien Gaulmin <julien.gaulmin@alcove.fr> and
13 * Nicolas Ferre <nicolas.ferre@alcove.fr> to support ARM7TDMI. Only
14 * very minor changes required to also work with StrongArm and presumably
15 * all ARM based systems.
17 * Based almost entirely on the Linux modutils-2.3.11 implementation.
18 * Copyright 1996, 1997 Linux International.
19 * New implementation contributed by Richard Henderson <rth@tamu.edu>
20 * Based on original work by Bjorn Ekwall <bj0rn@blox.se>
21 * Restructured (and partly rewritten) by:
22 * Björn Ekwall <bj0rn@blox.se> February 1999
24 * This program is free software; you can redistribute it and/or modify
25 * it under the terms of the GNU General Public License as published by
26 * the Free Software Foundation; either version 2 of the License, or
27 * (at your option) any later version.
29 * This program is distributed in the hope that it will be useful,
30 * but WITHOUT ANY WARRANTY; without even the implied warranty of
31 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
32 * General Public License for more details.
34 * You should have received a copy of the GNU General Public License
35 * along with this program; if not, write to the Free Software
36 * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
50 #include <sys/utsname.h>
52 //----------------------------------------------------------------------------
53 //--------modutils module.h, lines 45-242
54 //----------------------------------------------------------------------------
56 /* Definitions for the Linux module syscall interface.
57 Copyright 1996, 1997 Linux International.
59 Contributed by Richard Henderson <rth@tamu.edu>
61 This file is part of the Linux modutils.
63 This program is free software; you can redistribute it and/or modify it
64 under the terms of the GNU General Public License as published by the
65 Free Software Foundation; either version 2 of the License, or (at your
66 option) any later version.
68 This program is distributed in the hope that it will be useful, but
69 WITHOUT ANY WARRANTY; without even the implied warranty of
70 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
71 General Public License for more details.
73 You should have received a copy of the GNU General Public License
74 along with this program; if not, write to the Free Software Foundation,
75 Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. */
78 #ifndef MODUTILS_MODULE_H
79 static const int MODUTILS_MODULE_H = 1;
81 #ident "$Id: insmod.c,v 1.36 2001/01/23 22:30:04 markw Exp $"
83 /* This file contains the structures used by the 2.0 and 2.1 kernels.
84 We do not use the kernel headers directly because we do not wish
85 to be dependant on a particular kernel version to compile insmod. */
88 /*======================================================================*/
89 /* The structures used by Linux 2.0. */
91 /* The symbol format used by get_kernel_syms(2). */
100 unsigned long module; /* kernel addresses */
104 struct old_module_symbol
110 struct old_symbol_table
112 int size; /* total, including string table!!! */
115 struct old_module_symbol symbol[0]; /* actual size defined by n_symbols */
116 struct old_module_ref ref[0]; /* actual size defined by n_refs */
119 struct old_mod_routines
122 unsigned long cleanup;
128 unsigned long ref; /* the list of modules that refer to me */
129 unsigned long symtab;
131 int size; /* size of module in pages */
132 unsigned long addr; /* address of module */
134 unsigned long cleanup; /* cleanup routine */
137 /* Sent to init_module(2) or'ed into the code size parameter. */
138 static const int OLD_MOD_AUTOCLEAN = 0x40000000; /* big enough, but no sign problems... */
140 int get_kernel_syms(struct old_kernel_sym *);
141 int old_sys_init_module(const char *name, char *code, unsigned codesize,
142 struct old_mod_routines *, struct old_symbol_table *);
144 /*======================================================================*/
145 /* For sizeof() which are related to the module platform and not to the
146 environment isnmod is running in, use sizeof_xx instead of sizeof(xx). */
148 #define tgt_sizeof_char sizeof(char)
149 #define tgt_sizeof_short sizeof(short)
150 #define tgt_sizeof_int sizeof(int)
151 #define tgt_sizeof_long sizeof(long)
152 #define tgt_sizeof_char_p sizeof(char *)
153 #define tgt_sizeof_void_p sizeof(void *)
154 #define tgt_long long
156 #if defined(__sparc__) && !defined(__sparc_v9__) && defined(ARCH_sparc64)
157 #undef tgt_sizeof_long
158 #undef tgt_sizeof_char_p
159 #undef tgt_sizeof_void_p
161 static const int tgt_sizeof_long = 8;
162 static const int tgt_sizeof_char_p = 8;
163 static const int tgt_sizeof_void_p = 8;
164 #define tgt_long long long
167 /*======================================================================*/
168 /* The structures used in Linux 2.1. */
170 /* Note: new_module_symbol does not use tgt_long intentionally */
171 struct new_module_symbol
177 struct new_module_persist;
179 struct new_module_ref
181 unsigned tgt_long dep; /* kernel addresses */
182 unsigned tgt_long ref;
183 unsigned tgt_long next_ref;
188 unsigned tgt_long size_of_struct; /* == sizeof(module) */
189 unsigned tgt_long next;
190 unsigned tgt_long name;
191 unsigned tgt_long size;
194 unsigned tgt_long flags; /* AUTOCLEAN et al */
199 unsigned tgt_long syms;
200 unsigned tgt_long deps;
201 unsigned tgt_long refs;
202 unsigned tgt_long init;
203 unsigned tgt_long cleanup;
204 unsigned tgt_long ex_table_start;
205 unsigned tgt_long ex_table_end;
207 unsigned tgt_long gp;
209 /* Everything after here is extension. */
210 unsigned tgt_long persist_start;
211 unsigned tgt_long persist_end;
212 unsigned tgt_long can_unload;
213 unsigned tgt_long runsize;
216 struct new_module_info
224 /* Bits of module.flags. */
225 static const int NEW_MOD_RUNNING = 1;
226 static const int NEW_MOD_DELETED = 2;
227 static const int NEW_MOD_AUTOCLEAN = 4;
228 static const int NEW_MOD_VISITED = 8;
229 static const int NEW_MOD_USED_ONCE = 16;
231 int new_sys_init_module(const char *name, const struct new_module *);
232 int query_module(const char *name, int which, void *buf, size_t bufsize,
235 /* Values for query_module's which. */
237 static const int QM_MODULES = 1;
238 static const int QM_DEPS = 2;
239 static const int QM_REFS = 3;
240 static const int QM_SYMBOLS = 4;
241 static const int QM_INFO = 5;
243 /*======================================================================*/
244 /* The system calls unchanged between 2.0 and 2.1. */
246 unsigned long create_module(const char *, size_t);
247 int delete_module(const char *);
250 #endif /* module.h */
252 //----------------------------------------------------------------------------
253 //--------end of modutils module.h
254 //----------------------------------------------------------------------------
258 //----------------------------------------------------------------------------
259 //--------modutils obj.h, lines 253-462
260 //----------------------------------------------------------------------------
262 /* Elf object file loading and relocation routines.
263 Copyright 1996, 1997 Linux International.
265 Contributed by Richard Henderson <rth@tamu.edu>
267 This file is part of the Linux modutils.
269 This program is free software; you can redistribute it and/or modify it
270 under the terms of the GNU General Public License as published by the
271 Free Software Foundation; either version 2 of the License, or (at your
272 option) any later version.
274 This program is distributed in the hope that it will be useful, but
275 WITHOUT ANY WARRANTY; without even the implied warranty of
276 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
277 General Public License for more details.
279 You should have received a copy of the GNU General Public License
280 along with this program; if not, write to the Free Software Foundation,
281 Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. */
284 #ifndef MODUTILS_OBJ_H
285 static const int MODUTILS_OBJ_H = 1;
287 #ident "$Id: insmod.c,v 1.36 2001/01/23 22:30:04 markw Exp $"
289 /* The relocatable object is manipulated using elfin types. */
295 /* Machine-specific elf macros for i386 et al. */
297 /* the SH changes have only been tested on the SH4 in =little endian= mode */
298 /* I'm not sure about big endian, so let's warn: */
300 #if (defined(__SH4__) || defined(__SH3__)) && defined(__BIG_ENDIAN__)
301 #error insmod.c may require changes for use on big endian SH4/SH3
304 /* it may or may not work on the SH1/SH2... So let's error on those
306 #if (defined(__sh__) && (!(defined(__SH3__) || defined(__SH4__))))
307 #error insmod.c may require changes for non-SH3/SH4 use
310 #define ELFCLASSM ELFCLASS32
311 #define ELFDATAM ELFDATA2LSB
317 #define MATCH_MACHINE(x) (x == EM_SH)
318 #define SHT_RELM SHT_RELA
319 #define Elf32_RelM Elf32_Rela
321 #elif defined(__arm__)
323 #define MATCH_MACHINE(x) (x == EM_ARM)
324 #define SHT_RELM SHT_REL
325 #define Elf32_RelM Elf32_Rel
327 #elif defined(__i386__)
329 /* presumably we can use these for anything but the SH and ARM*/
330 /* this is the previous behavior, but it does result in
331 insmod.c being broken on anything except i386 */
333 #define MATCH_MACHINE(x) (x == EM_386)
335 #define MATCH_MACHINE(x) (x == EM_386 || x == EM_486)
338 #define SHT_RELM SHT_REL
339 #define Elf32_RelM Elf32_Rel
342 #error insmod.c no platform specified
346 # if ELFCLASSM == ELFCLASS32
347 # define ElfW(x) Elf32_ ## x
348 # define ELFW(x) ELF32_ ## x
350 # define ElfW(x) Elf64_ ## x
351 # define ELFW(x) ELF64_ ## x
355 /* For some reason this is missing from libc5. */
356 #ifndef ELF32_ST_INFO
357 # define ELF32_ST_INFO(bind, type) (((bind) << 4) + ((type) & 0xf))
360 #ifndef ELF64_ST_INFO
361 # define ELF64_ST_INFO(bind, type) (((bind) << 4) + ((type) & 0xf))
364 struct obj_string_patch;
365 struct obj_symbol_patch;
372 struct obj_section *load_next;
378 struct obj_symbol *next; /* hash table link */
382 int secidx; /* the defining section index/module */
384 int ksymidx; /* for export to the kernel symtab */
385 int referenced; /* actually used in the link */
388 /* Hardcode the hash table size. We shouldn't be needing so many
389 symbols that we begin to degrade performance, and we get a big win
390 by giving the compiler a constant divisor. */
392 #define HASH_BUCKETS 521
398 struct obj_section **sections;
399 struct obj_section *load_order;
400 struct obj_section **load_order_search_start;
401 struct obj_string_patch *string_patches;
402 struct obj_symbol_patch *symbol_patches;
403 int (*symbol_cmp)(const char *, const char *);
404 unsigned long (*symbol_hash)(const char *);
405 unsigned long local_symtab_size;
406 struct obj_symbol **local_symtab;
407 struct obj_symbol *symtab[HASH_BUCKETS];
418 struct obj_string_patch
420 struct obj_string_patch *next;
422 ElfW(Addr) reloc_offset;
423 ElfW(Addr) string_offset;
426 struct obj_symbol_patch
428 struct obj_symbol_patch *next;
430 ElfW(Addr) reloc_offset;
431 struct obj_symbol *sym;
435 /* Generic object manipulation routines. */
437 unsigned long obj_elf_hash(const char *);
439 unsigned long obj_elf_hash_n(const char *, unsigned long len);
441 struct obj_symbol *obj_add_symbol (struct obj_file *f, const char *name,
442 unsigned long symidx, int info, int secidx,
443 ElfW(Addr) value, unsigned long size);
445 struct obj_symbol *obj_find_symbol (struct obj_file *f,
448 ElfW(Addr) obj_symbol_final_value(struct obj_file *f,
449 struct obj_symbol *sym);
451 void obj_set_symbol_compare(struct obj_file *f,
452 int (*cmp)(const char *, const char *),
453 unsigned long (*hash)(const char *));
455 struct obj_section *obj_find_section (struct obj_file *f,
458 void obj_insert_section_load_order (struct obj_file *f,
459 struct obj_section *sec);
461 struct obj_section *obj_create_alloced_section (struct obj_file *f,
466 struct obj_section *obj_create_alloced_section_first (struct obj_file *f,
471 void *obj_extend_section (struct obj_section *sec, unsigned long more);
473 int obj_string_patch(struct obj_file *f, int secidx, ElfW(Addr) offset,
476 int obj_symbol_patch(struct obj_file *f, int secidx, ElfW(Addr) offset,
477 struct obj_symbol *sym);
479 int obj_check_undefineds(struct obj_file *f);
481 void obj_allocate_commons(struct obj_file *f);
483 unsigned long obj_load_size (struct obj_file *f);
485 int obj_relocate (struct obj_file *f, ElfW(Addr) base);
487 struct obj_file *obj_load(FILE *f);
489 int obj_create_image (struct obj_file *f, char *image);
491 /* Architecture specific manipulation routines. */
493 struct obj_file *arch_new_file (void);
495 struct obj_section *arch_new_section (void);
497 struct obj_symbol *arch_new_symbol (void);
499 enum obj_reloc arch_apply_relocation (struct obj_file *f,
500 struct obj_section *targsec,
501 struct obj_section *symsec,
502 struct obj_symbol *sym,
503 ElfW(RelM) *rel, ElfW(Addr) value);
505 int arch_create_got (struct obj_file *f);
508 int arch_init_module (struct obj_file *f, struct new_module *);
511 //----------------------------------------------------------------------------
512 //--------end of modutils obj.h
513 //----------------------------------------------------------------------------
519 #define _PATH_MODULES "/lib/modules"
520 static const int STRVERSIONLEN = 32;
522 #if !defined(BB_FEATURE_INSMOD_NEW_KERNEL) && !defined(BB_FEATURE_INSMOD_OLD_KERNEL)
523 #error "Must have ether BB_FEATURE_INSMOD_NEW_KERNEL or BB_FEATURE_INSMOD_OLD_KERNEL defined"
526 /*======================================================================*/
528 int flag_force_load = 0;
529 int flag_autoclean = 0;
530 int flag_verbose = 0;
534 /*======================================================================*/
536 /* previously, these were named i386_* but since we could be
537 compiling for the sh, I've renamed them to the more general
538 arch_* These structures are the same between the x86 and SH,
539 and we can't support anything else right now anyway. In the
540 future maybe they should be #if defined'd */
549 int inited:1; /* has been set up */
553 struct arch_got_entry {
555 unsigned offset_done:1;
556 unsigned reloc_done:1;
560 struct obj_file root;
562 struct obj_section *plt;
564 struct obj_section *got;
568 struct obj_symbol root;
570 struct arm_plt_entry pltent;
572 struct arch_got_entry gotent;
576 struct external_module {
581 struct new_module_symbol *syms;
584 struct new_module_symbol *ksyms;
587 struct external_module *ext_modules;
589 int n_ext_modules_used;
593 /* Some firendly syscalls to cheer everyone's day... */
594 #define __NR_new_sys_init_module __NR_init_module
595 _syscall2(int, new_sys_init_module, const char *, name,
596 const struct new_module *, info)
597 #define __NR_old_sys_init_module __NR_init_module
598 _syscall5(int, old_sys_init_module, const char *, name, char *, code,
599 unsigned, codesize, struct old_mod_routines *, routines,
600 struct old_symbol_table *, symtab)
602 _syscall1(int, delete_module, const char *, name)
604 extern int delete_module(const char *);
607 /* This is kind of troublesome. See, we don't actually support
608 the m68k or the arm the same way we support i386 and (now)
609 sh. In doing my SH patch, I just assumed that whatever works
610 for i386 also works for m68k and arm since currently insmod.c
611 does nothing special for them. If this isn't true, the below
612 line is rather misleading IMHO, and someone should either
613 change it or add more proper architecture-dependent support
616 -- Bryan Rittmeyer <bryan@ixiacom.com> */
618 #ifdef BB_FEATURE_INSMOD_OLD_KERNEL
619 _syscall1(int, get_kernel_syms, struct old_kernel_sym *, ks)
622 #if defined(__i386__) || defined(__m68k__) || defined(__arm__)
623 /* Jump through hoops to fixup error return codes */
624 #define __NR__create_module __NR_create_module
625 static inline _syscall2(long, _create_module, const char *, name, size_t,
627 unsigned long create_module(const char *name, size_t size)
629 long ret = _create_module(name, size);
631 if (ret == -1 && errno > 125) {
638 _syscall2(unsigned long, create_module, const char *, name, size_t, size)
640 static char m_filename[BUFSIZ + 1] = "\0";
641 static char m_fullName[BUFSIZ + 1] = "\0";
643 /*======================================================================*/
646 static int findNamedModule(const char *fileName, struct stat *statbuf,
649 char *fullName = (char *) userDate;
652 if (fullName[0] == '\0')
655 char *tmp = strrchr((char *) fileName, '/');
658 tmp = (char *) fileName;
661 if (check_wildcard_match(tmp, fullName) == TRUE) {
662 /* Stop searching if we find a match */
663 memcpy(m_filename, fileName, strlen(fileName)+1);
671 /*======================================================================*/
673 struct obj_file *arch_new_file(void)
676 f = xmalloc(sizeof(*f));
681 struct obj_section *arch_new_section(void)
683 return xmalloc(sizeof(struct obj_section));
686 struct obj_symbol *arch_new_symbol(void)
688 struct arch_symbol *sym;
689 sym = xmalloc(sizeof(*sym));
690 memset(&sym->gotent, 0, sizeof(sym->gotent));
695 arch_apply_relocation(struct obj_file *f,
696 struct obj_section *targsec,
697 struct obj_section *symsec,
698 struct obj_symbol *sym,
699 ElfW(RelM) *rel, ElfW(Addr) v)
701 struct arch_file *ifile = (struct arch_file *) f;
702 struct arch_symbol *isym = (struct arch_symbol *) sym;
704 ElfW(Addr) *loc = (ElfW(Addr) *) (targsec->contents + rel->r_offset);
705 ElfW(Addr) dot = targsec->header.sh_addr + rel->r_offset;
706 ElfW(Addr) got = ifile->got ? ifile->got->header.sh_addr : 0;
708 ElfW(Addr) plt = ifile->plt ? ifile->plt->header.sh_addr : 0;
710 struct arm_plt_entry *pe;
714 enum obj_reloc ret = obj_reloc_ok;
716 switch (ELF32_R_TYPE(rel->r_info)) {
718 /* even though these constants seem to be the same for
719 the i386 and the sh, we "#if define" them for clarity
720 and in case that ever changes */
723 #elif defined(__arm__)
725 #elif defined(__i386__)
732 #elif defined(__arm__)
734 #elif defined(__i386__)
741 #elif defined(__sh__)
745 #elif defined(__i386__)
756 #elif defined(__arm__)
759 /* find the plt entry and initialize it if necessary */
760 assert(isym != NULL);
761 pe = (struct arm_plt_entry*) &isym->pltent;
763 ip = (unsigned long *) (ifile->plt->contents + pe->offset);
764 ip[0] = 0xe51ff004; /* ldr pc,[pc,#-4] */
765 ip[1] = v; /* sym@ */
769 /* relative distance to target */
771 /* if the target is too far away.... */
772 if ((int)v < -0x02000000 || (int)v >= 0x02000000) {
774 v = plt + pe->offset - dot;
777 ret = obj_reloc_dangerous;
779 /* Convert to words. */
782 /* merge the offset into the instruction. */
783 *loc = (*loc & ~0x00ffffff) | ((v + *loc) & 0x00ffffff);
785 #elif defined(__i386__)
790 #elif defined(__sh__)
795 #elif defined(__i386__)
803 #elif defined(__sh__)
805 *loc += f->baseaddr + rel->r_addend;
807 #elif defined(__i386__)
815 #elif defined(__arm__)
817 #elif defined(__i386__)
822 *loc += got - dot + rel->r_addend;;
823 #elif defined(__i386__) || defined(__arm__)
830 #elif defined(__arm__)
832 #elif defined(__i386__)
835 assert(isym != NULL);
836 /* needs an entry in the .got: set it, once */
837 if (!isym->gotent.reloc_done) {
838 isym->gotent.reloc_done = 1;
839 *(ElfW(Addr) *) (ifile->got->contents + isym->gotent.offset) = v;
841 /* make the reloc with_respect_to_.got */
843 *loc += isym->gotent.offset + rel->r_addend;
844 #elif defined(__i386__) || defined(__arm__)
845 *loc += isym->gotent.offset;
849 /* address relative to the got */
852 #elif defined(__arm__)
854 #elif defined(__i386__)
862 printf("Warning: unhandled reloc %d\n",(int)ELF32_R_TYPE(rel->r_info));
863 ret = obj_reloc_unhandled;
870 int arch_create_got(struct obj_file *f)
872 struct arch_file *ifile = (struct arch_file *) f;
873 int i, got_offset = 0, gotneeded = 0;
875 int plt_offset = 0, pltneeded = 0;
877 struct obj_section *relsec, *symsec, *strsec;
878 ElfW(RelM) *rel, *relend;
879 ElfW(Sym) *symtab, *extsym;
880 const char *strtab, *name;
881 struct arch_symbol *intsym;
883 for (i = 0; i < f->header.e_shnum; ++i) {
884 relsec = f->sections[i];
885 if (relsec->header.sh_type != SHT_RELM)
888 symsec = f->sections[relsec->header.sh_link];
889 strsec = f->sections[symsec->header.sh_link];
891 rel = (ElfW(RelM) *) relsec->contents;
892 relend = rel + (relsec->header.sh_size / sizeof(ElfW(RelM)));
893 symtab = (ElfW(Sym) *) symsec->contents;
894 strtab = (const char *) strsec->contents;
896 for (; rel < relend; ++rel) {
897 extsym = &symtab[ELF32_R_SYM(rel->r_info)];
899 switch (ELF32_R_TYPE(rel->r_info)) {
902 #elif defined(__sh__)
904 #elif defined(__i386__)
920 #elif defined(__sh__)
924 #elif defined(__i386__)
934 if (extsym->st_name != 0) {
935 name = strtab + extsym->st_name;
937 name = f->sections[extsym->st_shndx]->name;
939 intsym = (struct arch_symbol *) obj_find_symbol(f, name);
941 if (!intsym->gotent.offset_done) {
942 intsym->gotent.offset_done = 1;
943 intsym->gotent.offset = got_offset;
947 if (pltneeded && intsym->pltent.allocated == 0) {
948 intsym->pltent.allocated = 1;
949 intsym->pltent.offset = plt_offset;
951 intsym->pltent.inited = 0;
960 struct obj_section* relsec = obj_find_section(f, ".got");
963 obj_extend_section(relsec, got_offset);
965 relsec = obj_create_alloced_section(f, ".got", 8, got_offset);
973 ifile->plt = obj_create_alloced_section(f, ".plt", 8, plt_offset);
975 if (got_offset > 0 || gotneeded)
976 ifile->got = obj_create_alloced_section(f, ".got", 4, got_offset);
982 int arch_init_module(struct obj_file *f, struct new_module *mod)
988 /*======================================================================*/
990 /* Standard ELF hash function. */
991 inline unsigned long obj_elf_hash_n(const char *name, unsigned long n)
1000 if ((g = (h & 0xf0000000)) != 0) {
1009 unsigned long obj_elf_hash(const char *name)
1011 return obj_elf_hash_n(name, strlen(name));
1014 #ifdef BB_FEATURE_INSMOD_VERSION_CHECKING
1015 /* Get the kernel version in the canonical integer form. */
1017 static int get_kernel_version(char str[STRVERSIONLEN])
1019 struct utsname uts_info;
1023 if (uname(&uts_info) < 0)
1025 strncpy(str, uts_info.release, STRVERSIONLEN);
1026 p = uts_info.release;
1028 a = strtoul(p, &p, 10);
1031 b = strtoul(p + 1, &p, 10);
1034 c = strtoul(p + 1, &q, 10);
1038 return a << 16 | b << 8 | c;
1041 /* String comparison for non-co-versioned kernel and module. */
1043 static int ncv_strcmp(const char *a, const char *b)
1045 size_t alen = strlen(a), blen = strlen(b);
1047 if (blen == alen + 10 && b[alen] == '_' && b[alen + 1] == 'R')
1048 return strncmp(a, b, alen);
1049 else if (alen == blen + 10 && a[blen] == '_' && a[blen + 1] == 'R')
1050 return strncmp(a, b, blen);
1052 return strcmp(a, b);
1055 /* String hashing for non-co-versioned kernel and module. Here
1056 we are simply forced to drop the crc from the hash. */
1058 static unsigned long ncv_symbol_hash(const char *str)
1060 size_t len = strlen(str);
1061 if (len > 10 && str[len - 10] == '_' && str[len - 9] == 'R')
1063 return obj_elf_hash_n(str, len);
1067 obj_set_symbol_compare(struct obj_file *f,
1068 int (*cmp) (const char *, const char *),
1069 unsigned long (*hash) (const char *))
1072 f->symbol_cmp = cmp;
1074 struct obj_symbol *tmptab[HASH_BUCKETS], *sym, *next;
1077 f->symbol_hash = hash;
1079 memcpy(tmptab, f->symtab, sizeof(tmptab));
1080 memset(f->symtab, 0, sizeof(f->symtab));
1082 for (i = 0; i < HASH_BUCKETS; ++i)
1083 for (sym = tmptab[i]; sym; sym = next) {
1084 unsigned long h = hash(sym->name) % HASH_BUCKETS;
1086 sym->next = f->symtab[h];
1092 #endif /* BB_FEATURE_INSMOD_VERSION_CHECKING */
1095 struct obj_symbol *obj_add_symbol(struct obj_file *f, const char *name,
1096 unsigned long symidx, int info,
1097 int secidx, ElfW(Addr) value,
1100 struct obj_symbol *sym;
1101 unsigned long hash = f->symbol_hash(name) % HASH_BUCKETS;
1102 int n_type = ELFW(ST_TYPE) (info);
1103 int n_binding = ELFW(ST_BIND) (info);
1105 for (sym = f->symtab[hash]; sym; sym = sym->next)
1106 if (f->symbol_cmp(sym->name, name) == 0) {
1107 int o_secidx = sym->secidx;
1108 int o_info = sym->info;
1109 int o_type = ELFW(ST_TYPE) (o_info);
1110 int o_binding = ELFW(ST_BIND) (o_info);
1112 /* A redefinition! Is it legal? */
1114 if (secidx == SHN_UNDEF)
1116 else if (o_secidx == SHN_UNDEF)
1118 else if (n_binding == STB_GLOBAL && o_binding == STB_LOCAL) {
1119 /* Cope with local and global symbols of the same name
1120 in the same object file, as might have been created
1121 by ld -r. The only reason locals are now seen at this
1122 level at all is so that we can do semi-sensible things
1125 struct obj_symbol *nsym, **p;
1127 nsym = arch_new_symbol();
1128 nsym->next = sym->next;
1131 /* Excise the old (local) symbol from the hash chain. */
1132 for (p = &f->symtab[hash]; *p != sym; p = &(*p)->next)
1136 } else if (n_binding == STB_LOCAL) {
1137 /* Another symbol of the same name has already been defined.
1138 Just add this to the local table. */
1139 sym = arch_new_symbol();
1142 f->local_symtab[symidx] = sym;
1144 } else if (n_binding == STB_WEAK)
1146 else if (o_binding == STB_WEAK)
1148 /* Don't unify COMMON symbols with object types the programmer
1150 else if (secidx == SHN_COMMON
1151 && (o_type == STT_NOTYPE || o_type == STT_OBJECT))
1153 else if (o_secidx == SHN_COMMON
1154 && (n_type == STT_NOTYPE || n_type == STT_OBJECT))
1157 /* Don't report an error if the symbol is coming from
1158 the kernel or some external module. */
1159 if (secidx <= SHN_HIRESERVE)
1160 error_msg("%s multiply defined\n", name);
1165 /* Completely new symbol. */
1166 sym = arch_new_symbol();
1167 sym->next = f->symtab[hash];
1168 f->symtab[hash] = sym;
1171 if (ELFW(ST_BIND) (info) == STB_LOCAL)
1172 f->local_symtab[symidx] = sym;
1178 sym->secidx = secidx;
1184 struct obj_symbol *obj_find_symbol(struct obj_file *f, const char *name)
1186 struct obj_symbol *sym;
1187 unsigned long hash = f->symbol_hash(name) % HASH_BUCKETS;
1189 for (sym = f->symtab[hash]; sym; sym = sym->next)
1190 if (f->symbol_cmp(sym->name, name) == 0)
1197 obj_symbol_final_value(struct obj_file * f, struct obj_symbol * sym)
1200 if (sym->secidx >= SHN_LORESERVE)
1203 return sym->value + f->sections[sym->secidx]->header.sh_addr;
1205 /* As a special case, a NULL sym has value zero. */
1210 struct obj_section *obj_find_section(struct obj_file *f, const char *name)
1212 int i, n = f->header.e_shnum;
1214 for (i = 0; i < n; ++i)
1215 if (strcmp(f->sections[i]->name, name) == 0)
1216 return f->sections[i];
1221 static int obj_load_order_prio(struct obj_section *a)
1223 unsigned long af, ac;
1225 af = a->header.sh_flags;
1228 if (a->name[0] != '.' || strlen(a->name) != 10 ||
1229 strcmp(a->name + 5, ".init"))
1233 if (!(af & SHF_WRITE))
1235 if (af & SHF_EXECINSTR)
1237 if (a->header.sh_type != SHT_NOBITS)
1244 obj_insert_section_load_order(struct obj_file *f, struct obj_section *sec)
1246 struct obj_section **p;
1247 int prio = obj_load_order_prio(sec);
1248 for (p = f->load_order_search_start; *p; p = &(*p)->load_next)
1249 if (obj_load_order_prio(*p) < prio)
1251 sec->load_next = *p;
1255 struct obj_section *obj_create_alloced_section(struct obj_file *f,
1257 unsigned long align,
1260 int newidx = f->header.e_shnum++;
1261 struct obj_section *sec;
1263 f->sections = xrealloc(f->sections, (newidx + 1) * sizeof(sec));
1264 f->sections[newidx] = sec = arch_new_section();
1266 memset(sec, 0, sizeof(*sec));
1267 sec->header.sh_type = SHT_PROGBITS;
1268 sec->header.sh_flags = SHF_WRITE | SHF_ALLOC;
1269 sec->header.sh_size = size;
1270 sec->header.sh_addralign = align;
1274 sec->contents = xmalloc(size);
1276 obj_insert_section_load_order(f, sec);
1281 struct obj_section *obj_create_alloced_section_first(struct obj_file *f,
1283 unsigned long align,
1286 int newidx = f->header.e_shnum++;
1287 struct obj_section *sec;
1289 f->sections = xrealloc(f->sections, (newidx + 1) * sizeof(sec));
1290 f->sections[newidx] = sec = arch_new_section();
1292 memset(sec, 0, sizeof(*sec));
1293 sec->header.sh_type = SHT_PROGBITS;
1294 sec->header.sh_flags = SHF_WRITE | SHF_ALLOC;
1295 sec->header.sh_size = size;
1296 sec->header.sh_addralign = align;
1300 sec->contents = xmalloc(size);
1302 sec->load_next = f->load_order;
1303 f->load_order = sec;
1304 if (f->load_order_search_start == &f->load_order)
1305 f->load_order_search_start = &sec->load_next;
1310 void *obj_extend_section(struct obj_section *sec, unsigned long more)
1312 unsigned long oldsize = sec->header.sh_size;
1313 sec->contents = xrealloc(sec->contents, sec->header.sh_size += more);
1314 return sec->contents + oldsize;
1319 /* Conditionally add the symbols from the given symbol set to the
1325 int idx, struct new_module_symbol *syms, size_t nsyms)
1327 struct new_module_symbol *s;
1331 for (i = 0, s = syms; i < nsyms; ++i, ++s) {
1333 /* Only add symbols that are already marked external. If we
1334 override locals we may cause problems for argument initialization.
1335 We will also create a false dependency on the module. */
1336 struct obj_symbol *sym;
1338 sym = obj_find_symbol(f, (char *) s->name);
1339 if (sym && !ELFW(ST_BIND) (sym->info) == STB_LOCAL) {
1340 sym = obj_add_symbol(f, (char *) s->name, -1,
1341 ELFW(ST_INFO) (STB_GLOBAL, STT_NOTYPE),
1343 /* Did our symbol just get installed? If so, mark the
1344 module as "used". */
1345 if (sym->secidx == idx)
1353 static void add_kernel_symbols(struct obj_file *f)
1355 struct external_module *m;
1358 /* Add module symbols first. */
1360 for (i = 0, m = ext_modules; i < n_ext_modules; ++i, ++m)
1362 && add_symbols_from(f, SHN_HIRESERVE + 2 + i, m->syms,
1363 m->nsyms)) m->used = 1, ++nused;
1365 n_ext_modules_used = nused;
1367 /* And finally the symbols from the kernel proper. */
1370 add_symbols_from(f, SHN_HIRESERVE + 1, ksyms, nksyms);
1373 static char *get_modinfo_value(struct obj_file *f, const char *key)
1375 struct obj_section *sec;
1376 char *p, *v, *n, *ep;
1377 size_t klen = strlen(key);
1379 sec = obj_find_section(f, ".modinfo");
1383 ep = p + sec->header.sh_size;
1386 n = strchr(p, '\0');
1388 if (p + klen == v && strncmp(p, key, klen) == 0)
1391 if (p + klen == n && strcmp(p, key) == 0)
1401 /*======================================================================*/
1402 /* Functions relating to module loading in pre 2.1 kernels. */
1405 old_process_module_arguments(struct obj_file *f, int argc, char **argv)
1409 struct obj_symbol *sym;
1413 if ((q = strchr(p, '=')) == NULL) {
1419 sym = obj_find_symbol(f, p);
1421 /* Also check that the parameter was not resolved from the kernel. */
1422 if (sym == NULL || sym->secidx > SHN_HIRESERVE) {
1423 error_msg("symbol for parameter %s not found\n", p);
1427 loc = (int *) (f->sections[sym->secidx]->contents + sym->value);
1429 /* Do C quoting if we begin with a ". */
1433 str = alloca(strlen(q));
1434 for (r = str, q++; *q != '"'; ++q, ++r) {
1436 error_msg("improperly terminated string argument for %s\n", p);
1438 } else if (*q == '\\')
1472 if (q[1] >= '0' && q[1] <= '7') {
1473 c = (c * 8) + *++q - '0';
1474 if (q[1] >= '0' && q[1] <= '7')
1475 c = (c * 8) + *++q - '0';
1488 obj_string_patch(f, sym->secidx, sym->value, str);
1489 } else if (*q >= '0' && *q <= '9') {
1491 *loc++ = strtoul(q, &q, 0);
1492 while (*q++ == ',');
1494 char *contents = f->sections[sym->secidx]->contents;
1495 char *loc = contents + sym->value;
1496 char *r; /* To search for commas */
1498 /* Break the string with comas */
1499 while ((r = strchr(q, ',')) != (char *) NULL) {
1501 obj_string_patch(f, sym->secidx, loc - contents, q);
1502 loc += sizeof(char *);
1507 obj_string_patch(f, sym->secidx, loc - contents, q);
1516 #ifdef BB_FEATURE_INSMOD_VERSION_CHECKING
1517 static int old_is_module_checksummed(struct obj_file *f)
1519 return obj_find_symbol(f, "Using_Versions") != NULL;
1521 /* Get the module's kernel version in the canonical integer form. */
1524 old_get_module_version(struct obj_file *f, char str[STRVERSIONLEN])
1526 struct obj_symbol *sym;
1530 sym = obj_find_symbol(f, "kernel_version");
1534 p = f->sections[sym->secidx]->contents + sym->value;
1535 strncpy(str, p, STRVERSIONLEN);
1537 a = strtoul(p, &p, 10);
1540 b = strtoul(p + 1, &p, 10);
1543 c = strtoul(p + 1, &q, 10);
1547 return a << 16 | b << 8 | c;
1550 #endif /* BB_FEATURE_INSMOD_VERSION_CHECKING */
1552 #ifdef BB_FEATURE_INSMOD_OLD_KERNEL
1554 /* Fetch all the symbols and divvy them up as appropriate for the modules. */
1556 static int old_get_kernel_symbols(const char *m_name)
1558 struct old_kernel_sym *ks, *k;
1559 struct new_module_symbol *s;
1560 struct external_module *mod;
1561 int nks, nms, nmod, i;
1563 nks = get_kernel_syms(NULL);
1565 perror_msg("get_kernel_syms: %s", m_name);
1569 ks = k = xmalloc(nks * sizeof(*ks));
1571 if (get_kernel_syms(ks) != nks) {
1572 perror("inconsistency with get_kernel_syms -- is someone else "
1573 "playing with modules?");
1578 /* Collect the module information. */
1583 while (k->name[0] == '#' && k->name[1]) {
1584 struct old_kernel_sym *k2;
1585 struct new_module_symbol *s;
1587 /* Find out how many symbols this module has. */
1588 for (k2 = k + 1; k2->name[0] != '#'; ++k2)
1592 mod = xrealloc(mod, (++nmod + 1) * sizeof(*mod));
1593 mod[nmod].name = k->name + 1;
1594 mod[nmod].addr = k->value;
1596 mod[nmod].nsyms = nms;
1597 mod[nmod].syms = s = (nms ? xmalloc(nms * sizeof(*s)) : NULL);
1599 for (i = 0, ++k; i < nms; ++i, ++s, ++k) {
1600 s->name = (unsigned long) k->name;
1601 s->value = k->value;
1608 n_ext_modules = nmod + 1;
1610 /* Now collect the symbols for the kernel proper. */
1612 if (k->name[0] == '#')
1615 nksyms = nms = nks - (k - ks);
1616 ksyms = s = (nms ? xmalloc(nms * sizeof(*s)) : NULL);
1618 for (i = 0; i < nms; ++i, ++s, ++k) {
1619 s->name = (unsigned long) k->name;
1620 s->value = k->value;
1626 /* Return the kernel symbol checksum version, or zero if not used. */
1628 static int old_is_kernel_checksummed(void)
1630 /* Using_Versions is the first symbol. */
1632 && strcmp((char *) ksyms[0].name,
1633 "Using_Versions") == 0) return ksyms[0].value;
1639 static int old_create_mod_use_count(struct obj_file *f)
1641 struct obj_section *sec;
1643 sec = obj_create_alloced_section_first(f, ".moduse", sizeof(long),
1646 obj_add_symbol(f, "mod_use_count_", -1,
1647 ELFW(ST_INFO) (STB_LOCAL, STT_OBJECT), sec->idx, 0,
1654 old_init_module(const char *m_name, struct obj_file *f,
1655 unsigned long m_size)
1658 struct old_mod_routines routines;
1659 struct old_symbol_table *symtab;
1662 /* Create the symbol table */
1664 int nsyms = 0, strsize = 0, total;
1666 /* Size things first... */
1669 for (i = 0; i < HASH_BUCKETS; ++i) {
1670 struct obj_symbol *sym;
1671 for (sym = f->symtab[i]; sym; sym = sym->next)
1672 if (ELFW(ST_BIND) (sym->info) != STB_LOCAL
1673 && sym->secidx <= SHN_HIRESERVE)
1675 sym->ksymidx = nsyms++;
1676 strsize += strlen(sym->name) + 1;
1681 total = (sizeof(struct old_symbol_table)
1682 + nsyms * sizeof(struct old_module_symbol)
1683 + n_ext_modules_used * sizeof(struct old_module_ref)
1685 symtab = xmalloc(total);
1686 symtab->size = total;
1687 symtab->n_symbols = nsyms;
1688 symtab->n_refs = n_ext_modules_used;
1690 if (flag_export && nsyms) {
1691 struct old_module_symbol *ksym;
1695 ksym = symtab->symbol;
1696 str = ((char *) ksym + nsyms * sizeof(struct old_module_symbol)
1697 + n_ext_modules_used * sizeof(struct old_module_ref));
1699 for (i = 0; i < HASH_BUCKETS; ++i) {
1700 struct obj_symbol *sym;
1701 for (sym = f->symtab[i]; sym; sym = sym->next)
1702 if (sym->ksymidx >= 0) {
1703 ksym->addr = obj_symbol_final_value(f, sym);
1705 (unsigned long) str - (unsigned long) symtab;
1707 strcpy(str, sym->name);
1708 str += strlen(sym->name) + 1;
1714 if (n_ext_modules_used) {
1715 struct old_module_ref *ref;
1718 ref = (struct old_module_ref *)
1719 ((char *) symtab->symbol + nsyms * sizeof(struct old_module_symbol));
1721 for (i = 0; i < n_ext_modules; ++i)
1722 if (ext_modules[i].used)
1723 ref++->module = ext_modules[i].addr;
1727 /* Fill in routines. */
1730 obj_symbol_final_value(f, obj_find_symbol(f, "init_module"));
1732 obj_symbol_final_value(f, obj_find_symbol(f, "cleanup_module"));
1734 /* Whew! All of the initialization is complete. Collect the final
1735 module image and give it to the kernel. */
1737 image = xmalloc(m_size);
1738 obj_create_image(f, image);
1740 /* image holds the complete relocated module, accounting correctly for
1741 mod_use_count. However the old module kernel support assume that
1742 it is receiving something which does not contain mod_use_count. */
1743 ret = old_sys_init_module(m_name, image + sizeof(long),
1744 m_size | (flag_autoclean ? OLD_MOD_AUTOCLEAN
1745 : 0), &routines, symtab);
1747 perror_msg("init_module: %s", m_name);
1757 #define old_create_mod_use_count(x) TRUE
1758 #define old_init_module(x, y, z) TRUE
1760 #endif /* BB_FEATURE_INSMOD_OLD_KERNEL */
1764 /*======================================================================*/
1765 /* Functions relating to module loading after 2.1.18. */
1768 new_process_module_arguments(struct obj_file *f, int argc, char **argv)
1772 struct obj_symbol *sym;
1773 char *contents, *loc;
1777 if ((q = strchr(p, '=')) == NULL) {
1782 key = alloca(q - p + 6);
1783 memcpy(key, "parm_", 5);
1784 memcpy(key + 5, p, q - p);
1787 p = get_modinfo_value(f, key);
1790 error_msg("invalid parameter %s\n", key);
1794 sym = obj_find_symbol(f, key);
1796 /* Also check that the parameter was not resolved from the kernel. */
1797 if (sym == NULL || sym->secidx > SHN_HIRESERVE) {
1798 error_msg("symbol for parameter %s not found\n", key);
1803 min = strtoul(p, &p, 10);
1805 max = strtoul(p + 1, &p, 10);
1811 contents = f->sections[sym->secidx]->contents;
1812 loc = contents + sym->value;
1816 if ((*p == 's') || (*p == 'c')) {
1819 /* Do C quoting if we begin with a ", else slurp the lot. */
1823 str = alloca(strlen(q));
1824 for (r = str, q++; *q != '"'; ++q, ++r) {
1826 error_msg("improperly terminated string argument for %s\n",
1829 } else if (*q == '\\')
1863 if (q[1] >= '0' && q[1] <= '7') {
1864 c = (c * 8) + *++q - '0';
1865 if (q[1] >= '0' && q[1] <= '7')
1866 c = (c * 8) + *++q - '0';
1883 /* In this case, the string is not quoted. We will break
1884 it using the coma (like for ints). If the user wants to
1885 include comas in a string, he just has to quote it */
1887 /* Search the next coma */
1891 if (r != (char *) NULL) {
1892 /* Recopy the current field */
1893 str = alloca(r - q + 1);
1894 memcpy(str, q, r - q);
1896 /* I don't know if it is usefull, as the previous case
1897 doesn't null terminate the string ??? */
1900 /* Keep next fields */
1911 obj_string_patch(f, sym->secidx, loc - contents, str);
1912 loc += tgt_sizeof_char_p;
1914 /* Array of chars (in fact, matrix !) */
1915 unsigned long charssize; /* size of each member */
1917 /* Get the size of each member */
1918 /* Probably we should do that outside the loop ? */
1919 if (!isdigit(*(p + 1))) {
1920 error_msg("parameter type 'c' for %s must be followed by"
1921 " the maximum size\n", key);
1924 charssize = strtoul(p + 1, (char **) NULL, 10);
1927 if (strlen(str) >= charssize) {
1928 error_msg("string too long for %s (max %ld)\n", key,
1933 /* Copy to location */
1934 strcpy((char *) loc, str);
1938 long v = strtoul(q, &q, 0);
1945 loc += tgt_sizeof_short;
1949 loc += tgt_sizeof_int;
1953 loc += tgt_sizeof_long;
1957 error_msg("unknown parameter type '%c' for %s\n", *p, key);
1972 goto retry_end_of_value;
1976 error_msg("too many values for %s (max %d)\n", key, max);
1983 error_msg("invalid argument syntax for %s\n", key);
1990 error_msg("too few values for %s (min %d)\n", key, min);
2000 #ifdef BB_FEATURE_INSMOD_VERSION_CHECKING
2001 static int new_is_module_checksummed(struct obj_file *f)
2003 const char *p = get_modinfo_value(f, "using_checksums");
2010 /* Get the module's kernel version in the canonical integer form. */
2013 new_get_module_version(struct obj_file *f, char str[STRVERSIONLEN])
2018 p = get_modinfo_value(f, "kernel_version");
2021 strncpy(str, p, STRVERSIONLEN);
2023 a = strtoul(p, &p, 10);
2026 b = strtoul(p + 1, &p, 10);
2029 c = strtoul(p + 1, &q, 10);
2033 return a << 16 | b << 8 | c;
2036 #endif /* BB_FEATURE_INSMOD_VERSION_CHECKING */
2039 #ifdef BB_FEATURE_INSMOD_NEW_KERNEL
2041 /* Fetch the loaded modules, and all currently exported symbols. */
2043 static int new_get_kernel_symbols(void)
2045 char *module_names, *mn;
2046 struct external_module *modules, *m;
2047 struct new_module_symbol *syms, *s;
2048 size_t ret, bufsize, nmod, nsyms, i, j;
2050 /* Collect the loaded modules. */
2052 module_names = xmalloc(bufsize = 256);
2054 if (query_module(NULL, QM_MODULES, module_names, bufsize, &ret)) {
2055 if (errno == ENOSPC) {
2056 module_names = xrealloc(module_names, bufsize = ret);
2057 goto retry_modules_load;
2059 perror_msg("QM_MODULES");
2063 n_ext_modules = nmod = ret;
2064 ext_modules = modules = xmalloc(nmod * sizeof(*modules));
2065 memset(modules, 0, nmod * sizeof(*modules));
2067 /* Collect the modules' symbols. */
2069 for (i = 0, mn = module_names, m = modules;
2070 i < nmod; ++i, ++m, mn += strlen(mn) + 1) {
2071 struct new_module_info info;
2073 if (query_module(mn, QM_INFO, &info, sizeof(info), &ret)) {
2074 if (errno == ENOENT) {
2075 /* The module was removed out from underneath us. */
2078 perror_msg("query_module: QM_INFO: %s", mn);
2082 syms = xmalloc(bufsize = 1024);
2084 if (query_module(mn, QM_SYMBOLS, syms, bufsize, &ret)) {
2087 syms = xrealloc(syms, bufsize = ret);
2088 goto retry_mod_sym_load;
2090 /* The module was removed out from underneath us. */
2093 perror_msg("query_module: QM_SYMBOLS: %s", mn);
2100 m->addr = info.addr;
2104 for (j = 0, s = syms; j < nsyms; ++j, ++s) {
2105 s->name += (unsigned long) syms;
2109 /* Collect the kernel's symbols. */
2111 syms = xmalloc(bufsize = 16 * 1024);
2112 retry_kern_sym_load:
2113 if (query_module(NULL, QM_SYMBOLS, syms, bufsize, &ret)) {
2114 if (errno == ENOSPC) {
2115 syms = xrealloc(syms, bufsize = ret);
2116 goto retry_kern_sym_load;
2118 perror_msg("kernel: QM_SYMBOLS");
2121 nksyms = nsyms = ret;
2124 for (j = 0, s = syms; j < nsyms; ++j, ++s) {
2125 s->name += (unsigned long) syms;
2131 /* Return the kernel symbol checksum version, or zero if not used. */
2133 static int new_is_kernel_checksummed(void)
2135 struct new_module_symbol *s;
2138 /* Using_Versions is not the first symbol, but it should be in there. */
2140 for (i = 0, s = ksyms; i < nksyms; ++i, ++s)
2141 if (strcmp((char *) s->name, "Using_Versions") == 0)
2148 static int new_create_this_module(struct obj_file *f, const char *m_name)
2150 struct obj_section *sec;
2152 sec = obj_create_alloced_section_first(f, ".this", tgt_sizeof_long,
2153 sizeof(struct new_module));
2154 memset(sec->contents, 0, sizeof(struct new_module));
2156 obj_add_symbol(f, "__this_module", -1,
2157 ELFW(ST_INFO) (STB_LOCAL, STT_OBJECT), sec->idx, 0,
2158 sizeof(struct new_module));
2160 obj_string_patch(f, sec->idx, offsetof(struct new_module, name),
2167 static int new_create_module_ksymtab(struct obj_file *f)
2169 struct obj_section *sec;
2172 /* We must always add the module references. */
2174 if (n_ext_modules_used) {
2175 struct new_module_ref *dep;
2176 struct obj_symbol *tm;
2178 sec = obj_create_alloced_section(f, ".kmodtab", tgt_sizeof_void_p,
2179 (sizeof(struct new_module_ref)
2180 * n_ext_modules_used));
2184 tm = obj_find_symbol(f, "__this_module");
2185 dep = (struct new_module_ref *) sec->contents;
2186 for (i = 0; i < n_ext_modules; ++i)
2187 if (ext_modules[i].used) {
2188 dep->dep = ext_modules[i].addr;
2189 obj_symbol_patch(f, sec->idx,
2190 (char *) &dep->ref - sec->contents, tm);
2196 if (flag_export && !obj_find_section(f, "__ksymtab")) {
2201 obj_create_alloced_section(f, "__ksymtab", tgt_sizeof_void_p,
2204 /* We don't want to export symbols residing in sections that
2205 aren't loaded. There are a number of these created so that
2206 we make sure certain module options don't appear twice. */
2208 loaded = alloca(sizeof(int) * (i = f->header.e_shnum));
2210 loaded[i] = (f->sections[i]->header.sh_flags & SHF_ALLOC) != 0;
2212 for (nsyms = i = 0; i < HASH_BUCKETS; ++i) {
2213 struct obj_symbol *sym;
2214 for (sym = f->symtab[i]; sym; sym = sym->next)
2215 if (ELFW(ST_BIND) (sym->info) != STB_LOCAL
2216 && sym->secidx <= SHN_HIRESERVE
2217 && (sym->secidx >= SHN_LORESERVE
2218 || loaded[sym->secidx])) {
2219 ElfW(Addr) ofs = nsyms * 2 * tgt_sizeof_void_p;
2221 obj_symbol_patch(f, sec->idx, ofs, sym);
2222 obj_string_patch(f, sec->idx, ofs + tgt_sizeof_void_p,
2229 obj_extend_section(sec, nsyms * 2 * tgt_sizeof_char_p);
2237 new_init_module(const char *m_name, struct obj_file *f,
2238 unsigned long m_size)
2240 struct new_module *module;
2241 struct obj_section *sec;
2246 sec = obj_find_section(f, ".this");
2247 module = (struct new_module *) sec->contents;
2248 m_addr = sec->header.sh_addr;
2250 module->size_of_struct = sizeof(*module);
2251 module->size = m_size;
2252 module->flags = flag_autoclean ? NEW_MOD_AUTOCLEAN : 0;
2254 sec = obj_find_section(f, "__ksymtab");
2255 if (sec && sec->header.sh_size) {
2256 module->syms = sec->header.sh_addr;
2257 module->nsyms = sec->header.sh_size / (2 * tgt_sizeof_char_p);
2260 if (n_ext_modules_used) {
2261 sec = obj_find_section(f, ".kmodtab");
2262 module->deps = sec->header.sh_addr;
2263 module->ndeps = n_ext_modules_used;
2267 obj_symbol_final_value(f, obj_find_symbol(f, "init_module"));
2269 obj_symbol_final_value(f, obj_find_symbol(f, "cleanup_module"));
2271 sec = obj_find_section(f, "__ex_table");
2273 module->ex_table_start = sec->header.sh_addr;
2274 module->ex_table_end = sec->header.sh_addr + sec->header.sh_size;
2277 sec = obj_find_section(f, ".text.init");
2279 module->runsize = sec->header.sh_addr - m_addr;
2281 sec = obj_find_section(f, ".data.init");
2283 if (!module->runsize ||
2284 module->runsize > sec->header.sh_addr - m_addr)
2285 module->runsize = sec->header.sh_addr - m_addr;
2288 if (!arch_init_module(f, module))
2291 /* Whew! All of the initialization is complete. Collect the final
2292 module image and give it to the kernel. */
2294 image = xmalloc(m_size);
2295 obj_create_image(f, image);
2297 ret = new_sys_init_module(m_name, (struct new_module *) image);
2299 perror_msg("init_module: %s", m_name);
2308 #define new_init_module(x, y, z) TRUE
2309 #define new_create_this_module(x, y) 0
2310 #define new_create_module_ksymtab(x)
2311 #define query_module(v, w, x, y, z) -1
2313 #endif /* BB_FEATURE_INSMOD_NEW_KERNEL */
2316 /*======================================================================*/
2319 obj_string_patch(struct obj_file *f, int secidx, ElfW(Addr) offset,
2322 struct obj_string_patch *p;
2323 struct obj_section *strsec;
2324 size_t len = strlen(string) + 1;
2327 p = xmalloc(sizeof(*p));
2328 p->next = f->string_patches;
2329 p->reloc_secidx = secidx;
2330 p->reloc_offset = offset;
2331 f->string_patches = p;
2333 strsec = obj_find_section(f, ".kstrtab");
2334 if (strsec == NULL) {
2335 strsec = obj_create_alloced_section(f, ".kstrtab", 1, len);
2336 p->string_offset = 0;
2337 loc = strsec->contents;
2339 p->string_offset = strsec->header.sh_size;
2340 loc = obj_extend_section(strsec, len);
2342 memcpy(loc, string, len);
2348 obj_symbol_patch(struct obj_file *f, int secidx, ElfW(Addr) offset,
2349 struct obj_symbol *sym)
2351 struct obj_symbol_patch *p;
2353 p = xmalloc(sizeof(*p));
2354 p->next = f->symbol_patches;
2355 p->reloc_secidx = secidx;
2356 p->reloc_offset = offset;
2358 f->symbol_patches = p;
2363 int obj_check_undefineds(struct obj_file *f)
2368 for (i = 0; i < HASH_BUCKETS; ++i) {
2369 struct obj_symbol *sym;
2370 for (sym = f->symtab[i]; sym; sym = sym->next)
2371 if (sym->secidx == SHN_UNDEF) {
2372 if (ELFW(ST_BIND) (sym->info) == STB_WEAK) {
2373 sym->secidx = SHN_ABS;
2376 error_msg("unresolved symbol %s\n", sym->name);
2385 void obj_allocate_commons(struct obj_file *f)
2387 struct common_entry {
2388 struct common_entry *next;
2389 struct obj_symbol *sym;
2390 } *common_head = NULL;
2394 for (i = 0; i < HASH_BUCKETS; ++i) {
2395 struct obj_symbol *sym;
2396 for (sym = f->symtab[i]; sym; sym = sym->next)
2397 if (sym->secidx == SHN_COMMON) {
2398 /* Collect all COMMON symbols and sort them by size so as to
2399 minimize space wasted by alignment requirements. */
2401 struct common_entry **p, *n;
2402 for (p = &common_head; *p; p = &(*p)->next)
2403 if (sym->size <= (*p)->sym->size)
2406 n = alloca(sizeof(*n));
2414 for (i = 1; i < f->local_symtab_size; ++i) {
2415 struct obj_symbol *sym = f->local_symtab[i];
2416 if (sym && sym->secidx == SHN_COMMON) {
2417 struct common_entry **p, *n;
2418 for (p = &common_head; *p; p = &(*p)->next)
2419 if (sym == (*p)->sym)
2421 else if (sym->size < (*p)->sym->size) {
2422 n = alloca(sizeof(*n));
2432 /* Find the bss section. */
2433 for (i = 0; i < f->header.e_shnum; ++i)
2434 if (f->sections[i]->header.sh_type == SHT_NOBITS)
2437 /* If for some reason there hadn't been one, create one. */
2438 if (i == f->header.e_shnum) {
2439 struct obj_section *sec;
2441 f->sections = xrealloc(f->sections, (i + 1) * sizeof(sec));
2442 f->sections[i] = sec = arch_new_section();
2443 f->header.e_shnum = i + 1;
2445 memset(sec, 0, sizeof(*sec));
2446 sec->header.sh_type = SHT_PROGBITS;
2447 sec->header.sh_flags = SHF_WRITE | SHF_ALLOC;
2452 /* Allocate the COMMONS. */
2454 ElfW(Addr) bss_size = f->sections[i]->header.sh_size;
2455 ElfW(Addr) max_align = f->sections[i]->header.sh_addralign;
2456 struct common_entry *c;
2458 for (c = common_head; c; c = c->next) {
2459 ElfW(Addr) align = c->sym->value;
2461 if (align > max_align)
2463 if (bss_size & (align - 1))
2464 bss_size = (bss_size | (align - 1)) + 1;
2467 c->sym->value = bss_size;
2469 bss_size += c->sym->size;
2472 f->sections[i]->header.sh_size = bss_size;
2473 f->sections[i]->header.sh_addralign = max_align;
2477 /* For the sake of patch relocation and parameter initialization,
2478 allocate zeroed data for NOBITS sections now. Note that after
2479 this we cannot assume NOBITS are really empty. */
2480 for (i = 0; i < f->header.e_shnum; ++i) {
2481 struct obj_section *s = f->sections[i];
2482 if (s->header.sh_type == SHT_NOBITS) {
2483 if (s->header.sh_size != 0)
2484 s->contents = memset(xmalloc(s->header.sh_size),
2485 0, s->header.sh_size);
2489 s->header.sh_type = SHT_PROGBITS;
2494 unsigned long obj_load_size(struct obj_file *f)
2496 unsigned long dot = 0;
2497 struct obj_section *sec;
2499 /* Finalize the positions of the sections relative to one another. */
2501 for (sec = f->load_order; sec; sec = sec->load_next) {
2504 align = sec->header.sh_addralign;
2505 if (align && (dot & (align - 1)))
2506 dot = (dot | (align - 1)) + 1;
2508 sec->header.sh_addr = dot;
2509 dot += sec->header.sh_size;
2515 int obj_relocate(struct obj_file *f, ElfW(Addr) base)
2517 int i, n = f->header.e_shnum;
2520 /* Finalize the addresses of the sections. */
2523 for (i = 0; i < n; ++i)
2524 f->sections[i]->header.sh_addr += base;
2526 /* And iterate over all of the relocations. */
2528 for (i = 0; i < n; ++i) {
2529 struct obj_section *relsec, *symsec, *targsec, *strsec;
2530 ElfW(RelM) * rel, *relend;
2534 relsec = f->sections[i];
2535 if (relsec->header.sh_type != SHT_RELM)
2538 symsec = f->sections[relsec->header.sh_link];
2539 targsec = f->sections[relsec->header.sh_info];
2540 strsec = f->sections[symsec->header.sh_link];
2542 rel = (ElfW(RelM) *) relsec->contents;
2543 relend = rel + (relsec->header.sh_size / sizeof(ElfW(RelM)));
2544 symtab = (ElfW(Sym) *) symsec->contents;
2545 strtab = (const char *) strsec->contents;
2547 for (; rel < relend; ++rel) {
2548 ElfW(Addr) value = 0;
2549 struct obj_symbol *intsym = NULL;
2550 unsigned long symndx;
2551 ElfW(Sym) * extsym = 0;
2554 /* Attempt to find a value to use for this relocation. */
2556 symndx = ELFW(R_SYM) (rel->r_info);
2558 /* Note we've already checked for undefined symbols. */
2560 extsym = &symtab[symndx];
2561 if (ELFW(ST_BIND) (extsym->st_info) == STB_LOCAL) {
2562 /* Local symbols we look up in the local table to be sure
2563 we get the one that is really intended. */
2564 intsym = f->local_symtab[symndx];
2566 /* Others we look up in the hash table. */
2568 if (extsym->st_name)
2569 name = strtab + extsym->st_name;
2571 name = f->sections[extsym->st_shndx]->name;
2572 intsym = obj_find_symbol(f, name);
2575 value = obj_symbol_final_value(f, intsym);
2576 intsym->referenced = 1;
2578 #if SHT_RELM == SHT_RELA
2579 #if defined(__alpha__) && defined(AXP_BROKEN_GAS)
2580 /* Work around a nasty GAS bug, that is fixed as of 2.7.0.9. */
2581 if (!extsym || !extsym->st_name ||
2582 ELFW(ST_BIND) (extsym->st_info) != STB_LOCAL)
2584 value += rel->r_addend;
2588 switch (arch_apply_relocation
2589 (f, targsec, symsec, intsym, rel, value)) {
2593 case obj_reloc_overflow:
2594 errmsg = "Relocation overflow";
2596 case obj_reloc_dangerous:
2597 errmsg = "Dangerous relocation";
2599 case obj_reloc_unhandled:
2600 errmsg = "Unhandled relocation";
2603 error_msg("%s of type %ld for %s\n", errmsg,
2604 (long) ELFW(R_TYPE) (rel->r_info),
2605 strtab + extsym->st_name);
2607 error_msg("%s of type %ld\n", errmsg,
2608 (long) ELFW(R_TYPE) (rel->r_info));
2616 /* Finally, take care of the patches. */
2618 if (f->string_patches) {
2619 struct obj_string_patch *p;
2620 struct obj_section *strsec;
2621 ElfW(Addr) strsec_base;
2622 strsec = obj_find_section(f, ".kstrtab");
2623 strsec_base = strsec->header.sh_addr;
2625 for (p = f->string_patches; p; p = p->next) {
2626 struct obj_section *targsec = f->sections[p->reloc_secidx];
2627 *(ElfW(Addr) *) (targsec->contents + p->reloc_offset)
2628 = strsec_base + p->string_offset;
2632 if (f->symbol_patches) {
2633 struct obj_symbol_patch *p;
2635 for (p = f->symbol_patches; p; p = p->next) {
2636 struct obj_section *targsec = f->sections[p->reloc_secidx];
2637 *(ElfW(Addr) *) (targsec->contents + p->reloc_offset)
2638 = obj_symbol_final_value(f, p->sym);
2645 int obj_create_image(struct obj_file *f, char *image)
2647 struct obj_section *sec;
2648 ElfW(Addr) base = f->baseaddr;
2650 for (sec = f->load_order; sec; sec = sec->load_next) {
2653 if (sec->header.sh_size == 0)
2656 secimg = image + (sec->header.sh_addr - base);
2658 /* Note that we allocated data for NOBITS sections earlier. */
2659 memcpy(secimg, sec->contents, sec->header.sh_size);
2665 /*======================================================================*/
2667 struct obj_file *obj_load(FILE * fp)
2670 ElfW(Shdr) * section_headers;
2674 /* Read the file header. */
2676 f = arch_new_file();
2677 memset(f, 0, sizeof(*f));
2678 f->symbol_cmp = strcmp;
2679 f->symbol_hash = obj_elf_hash;
2680 f->load_order_search_start = &f->load_order;
2682 fseek(fp, 0, SEEK_SET);
2683 if (fread(&f->header, sizeof(f->header), 1, fp) != 1) {
2684 perror_msg("error reading ELF header");
2688 if (f->header.e_ident[EI_MAG0] != ELFMAG0
2689 || f->header.e_ident[EI_MAG1] != ELFMAG1
2690 || f->header.e_ident[EI_MAG2] != ELFMAG2
2691 || f->header.e_ident[EI_MAG3] != ELFMAG3) {
2692 error_msg("not an ELF file\n");
2695 if (f->header.e_ident[EI_CLASS] != ELFCLASSM
2696 || f->header.e_ident[EI_DATA] != ELFDATAM
2697 || f->header.e_ident[EI_VERSION] != EV_CURRENT
2698 || !MATCH_MACHINE(f->header.e_machine)) {
2699 error_msg("ELF file not for this architecture\n");
2702 if (f->header.e_type != ET_REL) {
2703 error_msg("ELF file not a relocatable object\n");
2707 /* Read the section headers. */
2709 if (f->header.e_shentsize != sizeof(ElfW(Shdr))) {
2710 error_msg("section header size mismatch: %lu != %lu\n",
2711 (unsigned long) f->header.e_shentsize,
2712 (unsigned long) sizeof(ElfW(Shdr)));
2716 shnum = f->header.e_shnum;
2717 f->sections = xmalloc(sizeof(struct obj_section *) * shnum);
2718 memset(f->sections, 0, sizeof(struct obj_section *) * shnum);
2720 section_headers = alloca(sizeof(ElfW(Shdr)) * shnum);
2721 fseek(fp, f->header.e_shoff, SEEK_SET);
2722 if (fread(section_headers, sizeof(ElfW(Shdr)), shnum, fp) != shnum) {
2723 perror_msg("error reading ELF section headers");
2727 /* Read the section data. */
2729 for (i = 0; i < shnum; ++i) {
2730 struct obj_section *sec;
2732 f->sections[i] = sec = arch_new_section();
2733 memset(sec, 0, sizeof(*sec));
2735 sec->header = section_headers[i];
2738 switch (sec->header.sh_type) {
2749 if (sec->header.sh_size > 0) {
2750 sec->contents = xmalloc(sec->header.sh_size);
2751 fseek(fp, sec->header.sh_offset, SEEK_SET);
2752 if (fread(sec->contents, sec->header.sh_size, 1, fp) != 1) {
2753 perror_msg("error reading ELF section data");
2757 sec->contents = NULL;
2761 #if SHT_RELM == SHT_REL
2763 error_msg("RELA relocations not supported on this architecture\n");
2767 error_msg("REL relocations not supported on this architecture\n");
2772 if (sec->header.sh_type >= SHT_LOPROC) {
2773 /* Assume processor specific section types are debug
2774 info and can safely be ignored. If this is ever not
2775 the case (Hello MIPS?), don't put ifdefs here but
2776 create an arch_load_proc_section(). */
2780 error_msg("can't handle sections of type %ld\n",
2781 (long) sec->header.sh_type);
2786 /* Do what sort of interpretation as needed by each section. */
2788 shstrtab = f->sections[f->header.e_shstrndx]->contents;
2790 for (i = 0; i < shnum; ++i) {
2791 struct obj_section *sec = f->sections[i];
2792 sec->name = shstrtab + sec->header.sh_name;
2795 for (i = 0; i < shnum; ++i) {
2796 struct obj_section *sec = f->sections[i];
2798 if (sec->header.sh_flags & SHF_ALLOC)
2799 obj_insert_section_load_order(f, sec);
2801 switch (sec->header.sh_type) {
2804 unsigned long nsym, j;
2808 if (sec->header.sh_entsize != sizeof(ElfW(Sym))) {
2809 error_msg("symbol size mismatch: %lu != %lu\n",
2810 (unsigned long) sec->header.sh_entsize,
2811 (unsigned long) sizeof(ElfW(Sym)));
2815 nsym = sec->header.sh_size / sizeof(ElfW(Sym));
2816 strtab = f->sections[sec->header.sh_link]->contents;
2817 sym = (ElfW(Sym) *) sec->contents;
2819 /* Allocate space for a table of local symbols. */
2820 j = f->local_symtab_size = sec->header.sh_info;
2821 f->local_symtab = xmalloc(j *=
2822 sizeof(struct obj_symbol *));
2823 memset(f->local_symtab, 0, j);
2825 /* Insert all symbols into the hash table. */
2826 for (j = 1, ++sym; j < nsym; ++j, ++sym) {
2829 name = strtab + sym->st_name;
2831 name = f->sections[sym->st_shndx]->name;
2833 obj_add_symbol(f, name, j, sym->st_info, sym->st_shndx,
2834 sym->st_value, sym->st_size);
2840 if (sec->header.sh_entsize != sizeof(ElfW(RelM))) {
2841 error_msg("relocation entry size mismatch: %lu != %lu\n",
2842 (unsigned long) sec->header.sh_entsize,
2843 (unsigned long) sizeof(ElfW(RelM)));
2853 static void hide_special_symbols(struct obj_file *f)
2855 static const char *const specials[] = {
2862 struct obj_symbol *sym;
2863 const char *const *p;
2865 for (p = specials; *p; ++p)
2866 if ((sym = obj_find_symbol(f, *p)) != NULL)
2868 ELFW(ST_INFO) (STB_LOCAL, ELFW(ST_TYPE) (sym->info));
2873 extern int insmod_main( int argc, char **argv)
2879 unsigned long m_size;
2883 char m_name[BUFSIZ + 1] = "\0";
2884 int exit_status = EXIT_FAILURE;
2886 #ifdef BB_FEATURE_INSMOD_VERSION_CHECKING
2888 char k_strversion[STRVERSIONLEN];
2889 char m_strversion[STRVERSIONLEN];
2896 usage(insmod_usage);
2899 /* Parse any options */
2900 while (--argc > 0 && **(++argv) == '-') {
2901 while (*(++(*argv))) {
2903 case 'f': /* force loading */
2904 flag_force_load = 1;
2906 case 'k': /* module loaded by kerneld, auto-cleanable */
2909 case 'v': /* verbose output */
2912 case 'x': /* do not export externs */
2916 usage(insmod_usage);
2922 usage(insmod_usage);
2924 /* Grab the module name */
2925 if ((tmp = strrchr(*argv, '/')) != NULL) {
2932 if (len > 2 && tmp[len - 2] == '.' && tmp[len - 1] == 'o')
2934 memcpy(m_name, tmp, len);
2935 strcpy(m_fullName, m_name);
2936 strcat(m_fullName, ".o");
2938 /* Get a filedesc for the module */
2939 if ((fp = fopen(*argv, "r")) == NULL) {
2940 /* Hmpf. Could not open it. Search through _PATH_MODULES to find a module named m_name */
2941 if (recursive_action(_PATH_MODULES, TRUE, FALSE, FALSE,
2942 findNamedModule, 0, m_fullName) == FALSE)
2944 if (m_filename[0] == '\0'
2945 || ((fp = fopen(m_filename, "r")) == NULL))
2947 error_msg("No module named '%s' found in '%s'\n", m_fullName, _PATH_MODULES);
2948 return EXIT_FAILURE;
2951 error_msg_and_die("No module named '%s' found in '%s'\n", m_fullName, _PATH_MODULES);
2953 memcpy(m_filename, *argv, strlen(*argv));
2956 if ((f = obj_load(fp)) == NULL)
2957 perror_msg_and_die("Could not load the module");
2959 if (get_modinfo_value(f, "kernel_version") == NULL)
2964 #ifdef BB_FEATURE_INSMOD_VERSION_CHECKING
2965 /* Version correspondence? */
2967 k_version = get_kernel_version(k_strversion);
2968 if (m_has_modinfo) {
2969 m_version = new_get_module_version(f, m_strversion);
2971 m_version = old_get_module_version(f, m_strversion);
2972 if (m_version == -1) {
2973 error_msg("couldn't find the kernel version the module was "
2979 if (strncmp(k_strversion, m_strversion, STRVERSIONLEN) != 0) {
2980 if (flag_force_load) {
2981 error_msg("Warning: kernel-module version mismatch\n"
2982 "\t%s was compiled for kernel version %s\n"
2983 "\twhile this kernel is version %s\n",
2984 m_filename, m_strversion, k_strversion);
2986 error_msg("kernel-module version mismatch\n"
2987 "\t%s was compiled for kernel version %s\n"
2988 "\twhile this kernel is version %s.\n",
2989 m_filename, m_strversion, k_strversion);
2994 #endif /* BB_FEATURE_INSMOD_VERSION_CHECKING */
2996 k_new_syscalls = !query_module(NULL, 0, NULL, 0, NULL);
2998 if (k_new_syscalls) {
2999 #ifdef BB_FEATURE_INSMOD_NEW_KERNEL
3000 if (!new_get_kernel_symbols())
3002 k_crcs = new_is_kernel_checksummed();
3004 error_msg("Not configured to support new kernels\n");
3008 #ifdef BB_FEATURE_INSMOD_OLD_KERNEL
3009 if (!old_get_kernel_symbols(m_name))
3011 k_crcs = old_is_kernel_checksummed();
3013 error_msg("Not configured to support old kernels\n");
3018 #ifdef BB_FEATURE_INSMOD_VERSION_CHECKING
3020 m_crcs = new_is_module_checksummed(f);
3022 m_crcs = old_is_module_checksummed(f);
3024 if (m_crcs != k_crcs)
3025 obj_set_symbol_compare(f, ncv_strcmp, ncv_symbol_hash);
3026 #endif /* BB_FEATURE_INSMOD_VERSION_CHECKING */
3028 /* Let the module know about the kernel symbols. */
3029 add_kernel_symbols(f);
3031 /* Allocate common symbols, symbol tables, and string tables. */
3034 ? !new_create_this_module(f, m_name)
3035 : !old_create_mod_use_count(f))
3040 if (!obj_check_undefineds(f)) {
3043 obj_allocate_commons(f);
3045 if (optind < argc) {
3047 ? !new_process_module_arguments(f, argc - optind, argv + optind)
3048 : !old_process_module_arguments(f, argc - optind, argv + optind))
3055 hide_special_symbols(f);
3058 new_create_module_ksymtab(f);
3060 /* Find current size of the module */
3061 m_size = obj_load_size(f);
3065 m_addr = create_module(m_name, m_size);
3070 error_msg("A module named %s already exists\n", m_name);
3073 error_msg("Can't allocate kernel memory for module; needed %lu bytes\n",
3077 perror_msg("create_module: %s", m_name);
3081 if (!obj_relocate(f, m_addr)) {
3082 delete_module(m_name);
3087 ? !new_init_module(m_name, f, m_size)
3088 : !old_init_module(m_name, f, m_size))
3090 delete_module(m_name);
3094 exit_status = EXIT_SUCCESS;
3098 return(exit_status);