X-Git-Url: https://git.librecmc.org/?a=blobdiff_plain;ds=sidebyside;f=modutils%2Finsmod.c;h=6f3b7d0f46383441d086129e19481bc1515cf6b2;hb=be039374f3bd1c76535387ac4d079506804be270;hp=882fcf80f6d67036439c994b562e6cc249cdadb0;hpb=ea62077b850076c4d7dc3cf78ebd1888928c6ddf;p=oweals%2Fbusybox.git diff --git a/modutils/insmod.c b/modutils/insmod.c index 882fcf80f..6f3b7d0f4 100644 --- a/modutils/insmod.c +++ b/modutils/insmod.c @@ -40,7 +40,7 @@ * PowerPC specific code stolen from modutils-2.3.16, * written by Paul Mackerras, Copyright 1996, 1997 Linux International. * I've only tested the code on mpc8xx platforms in big-endian mode. - * Did some cleanup and added CONFIG_USE_xxx_ENTRIES... + * Did some cleanup and added USE_xxx_ENTRIES... * * Quinn Jensen added MIPS support 23-Feb-2001. * based on modutils-2.4.2 @@ -58,28 +58,28 @@ * Licensed under GPLv2 or later, see file LICENSE in this tarball for details. */ -#include "busybox.h" +#include "libbb.h" #include #include -#if !defined(CONFIG_FEATURE_2_4_MODULES) && \ - !defined(CONFIG_FEATURE_2_6_MODULES) -#define CONFIG_FEATURE_2_4_MODULES +#if !ENABLE_FEATURE_2_4_MODULES && !ENABLE_FEATURE_2_6_MODULES +#undef ENABLE_FEATURE_2_4_MODULES +#define ENABLE_FEATURE_2_4_MODULES 1 #endif -#if !defined(CONFIG_FEATURE_2_4_MODULES) +#if !ENABLE_FEATURE_2_4_MODULES #define insmod_ng_main insmod_main #endif -#if defined(CONFIG_FEATURE_2_6_MODULES) -extern int insmod_ng_main( int argc, char **argv); +#if ENABLE_FEATURE_2_6_MODULES +extern int insmod_ng_main(int argc, char **argv) MAIN_EXTERNALLY_VISIBLE; #endif -#if defined(CONFIG_FEATURE_2_4_MODULES) +#if ENABLE_FEATURE_2_4_MODULES -#ifdef CONFIG_FEATURE_INSMOD_LOADINKMEM +#if ENABLE_FEATURE_INSMOD_LOADINKMEM #define LOADBITS 0 #else #define LOADBITS 1 @@ -100,11 +100,11 @@ extern int insmod_ng_main( int argc, char **argv); #define SHT_RELM SHT_REL #define Elf32_RelM Elf32_Rel #define ELFCLASSM ELFCLASS32 -#define CONFIG_USE_PLT_ENTRIES -#define CONFIG_PLT_ENTRY_SIZE 8 -#define CONFIG_USE_GOT_ENTRIES -#define CONFIG_GOT_ENTRY_SIZE 8 -#define CONFIG_USE_SINGLE +#define USE_PLT_ENTRIES +#define PLT_ENTRY_SIZE 8 +#define USE_GOT_ENTRIES +#define GOT_ENTRY_SIZE 8 +#define USE_SINGLE #endif /* blackfin */ @@ -134,7 +134,7 @@ extern int insmod_ng_main( int argc, char **argv); #define SHT_RELM SHT_RELA #define Elf32_RelM Elf32_Rela #define ELFCLASSM ELFCLASS32 -#define CONFIG_USE_SINGLE +#define USE_SINGLE #define SYMBOL_PREFIX "_" #endif @@ -161,9 +161,9 @@ extern int insmod_ng_main( int argc, char **argv); #define SHT_RELM SHT_REL #define Elf32_RelM Elf32_Rel #define ELFCLASSM ELFCLASS32 -#define CONFIG_USE_GOT_ENTRIES -#define CONFIG_GOT_ENTRY_SIZE 4 -#define CONFIG_USE_SINGLE +#define USE_GOT_ENTRIES +#define GOT_ENTRY_SIZE 4 +#define USE_SINGLE #endif /* IA64, aka Itanium */ @@ -180,14 +180,14 @@ extern int insmod_ng_main( int argc, char **argv); #define SHT_RELM SHT_RELA #define Elf32_RelM Elf32_Rela #define ELFCLASSM ELFCLASS32 -#define CONFIG_USE_GOT_ENTRIES -#define CONFIG_GOT_ENTRY_SIZE 4 -#define CONFIG_USE_SINGLE +#define USE_GOT_ENTRIES +#define GOT_ENTRY_SIZE 4 +#define USE_SINGLE #endif /* Microblaze */ #if defined(__microblaze__) -#define CONFIG_USE_SINGLE +#define USE_SINGLE #define MATCH_MACHINE(x) (x == EM_XILINX_MICROBLAZE) #define SHT_RELM SHT_RELA #define Elf32_RelM Elf32_Rela @@ -230,11 +230,11 @@ extern int insmod_ng_main( int argc, char **argv); #define SHT_RELM SHT_RELA #define Elf32_RelM Elf32_Rela #define ELFCLASSM ELFCLASS32 -#define CONFIG_USE_PLT_ENTRIES -#define CONFIG_PLT_ENTRY_SIZE 16 -#define CONFIG_USE_PLT_LIST -#define CONFIG_LIST_ARCHTYPE ElfW(Addr) -#define CONFIG_USE_LIST +#define USE_PLT_ENTRIES +#define PLT_ENTRY_SIZE 16 +#define USE_PLT_LIST +#define LIST_ARCHTYPE ElfW(Addr) +#define USE_LIST #define ARCHDATAM "__ftr_fixup" #endif @@ -244,11 +244,11 @@ extern int insmod_ng_main( int argc, char **argv); #define SHT_RELM SHT_RELA #define Elf32_RelM Elf32_Rela #define ELFCLASSM ELFCLASS32 -#define CONFIG_USE_PLT_ENTRIES -#define CONFIG_PLT_ENTRY_SIZE 8 -#define CONFIG_USE_GOT_ENTRIES -#define CONFIG_GOT_ENTRY_SIZE 8 -#define CONFIG_USE_SINGLE +#define USE_PLT_ENTRIES +#define PLT_ENTRY_SIZE 8 +#define USE_GOT_ENTRIES +#define GOT_ENTRY_SIZE 8 +#define USE_SINGLE #endif /* SuperH */ @@ -257,9 +257,9 @@ extern int insmod_ng_main( int argc, char **argv); #define SHT_RELM SHT_RELA #define Elf32_RelM Elf32_Rela #define ELFCLASSM ELFCLASS32 -#define CONFIG_USE_GOT_ENTRIES -#define CONFIG_GOT_ENTRY_SIZE 4 -#define CONFIG_USE_SINGLE +#define USE_GOT_ENTRIES +#define GOT_ENTRY_SIZE 4 +#define USE_SINGLE /* the SH changes have only been tested in =little endian= mode */ /* I'm not sure about big endian, so let's warn: */ #if defined(__sh__) && BB_BIG_ENDIAN @@ -280,14 +280,14 @@ extern int insmod_ng_main( int argc, char **argv); #endif /* v850e */ -#if defined (__v850e__) +#if defined(__v850e__) #define MATCH_MACHINE(x) ((x) == EM_V850 || (x) == EM_CYGNUS_V850) #define SHT_RELM SHT_RELA #define Elf32_RelM Elf32_Rela #define ELFCLASSM ELFCLASS32 -#define CONFIG_USE_PLT_ENTRIES -#define CONFIG_PLT_ENTRY_SIZE 8 -#define CONFIG_USE_SINGLE +#define USE_PLT_ENTRIES +#define PLT_ENTRY_SIZE 8 +#define USE_SINGLE #ifndef EM_CYGNUS_V850 /* grumble */ #define EM_CYGNUS_V850 0x9080 #endif @@ -298,9 +298,9 @@ extern int insmod_ng_main( int argc, char **argv); #if defined(__x86_64__) #define MATCH_MACHINE(x) (x == EM_X86_64) #define SHT_RELM SHT_RELA -#define CONFIG_USE_GOT_ENTRIES -#define CONFIG_GOT_ENTRY_SIZE 8 -#define CONFIG_USE_SINGLE +#define USE_GOT_ENTRIES +#define GOT_ENTRY_SIZE 8 +#define USE_SINGLE #define Elf64_RelM Elf64_Rela #define ELFCLASSM ELFCLASS64 #endif @@ -337,7 +337,6 @@ extern int insmod_ng_main( int argc, char **argv); #ifndef MODUTILS_MODULE_H -/* Why? static const int MODUTILS_MODULE_H = 1;*/ /*======================================================================*/ /* For sizeof() which are related to the module platform and not to the @@ -494,11 +493,9 @@ int delete_module(const char *); #ifndef MODUTILS_OBJ_H -/* Why? static const int MODUTILS_OBJ_H = 1; */ /* The relocatable object is manipulated using elfin types. */ -#include #include #include @@ -600,35 +597,35 @@ static unsigned long obj_elf_hash(const char *); static unsigned long obj_elf_hash_n(const char *, unsigned long len); -static struct obj_symbol *obj_find_symbol (struct obj_file *f, +static struct obj_symbol *obj_find_symbol(struct obj_file *f, const char *name); static ElfW(Addr) obj_symbol_final_value(struct obj_file *f, struct obj_symbol *sym); -#ifdef CONFIG_FEATURE_INSMOD_VERSION_CHECKING +#if ENABLE_FEATURE_INSMOD_VERSION_CHECKING static void obj_set_symbol_compare(struct obj_file *f, int (*cmp)(const char *, const char *), unsigned long (*hash)(const char *)); #endif -static struct obj_section *obj_find_section (struct obj_file *f, +static struct obj_section *obj_find_section(struct obj_file *f, const char *name); -static void obj_insert_section_load_order (struct obj_file *f, +static void obj_insert_section_load_order(struct obj_file *f, struct obj_section *sec); -static struct obj_section *obj_create_alloced_section (struct obj_file *f, +static struct obj_section *obj_create_alloced_section(struct obj_file *f, const char *name, unsigned long align, unsigned long size); -static struct obj_section *obj_create_alloced_section_first (struct obj_file *f, +static struct obj_section *obj_create_alloced_section_first(struct obj_file *f, const char *name, unsigned long align, unsigned long size); -static void *obj_extend_section (struct obj_section *sec, unsigned long more); +static void *obj_extend_section(struct obj_section *sec, unsigned long more); static int obj_string_patch(struct obj_file *f, int secidx, ElfW(Addr) offset, const char *string); @@ -640,32 +637,32 @@ static int obj_check_undefineds(struct obj_file *f); static void obj_allocate_commons(struct obj_file *f); -static unsigned long obj_load_size (struct obj_file *f); +static unsigned long obj_load_size(struct obj_file *f); -static int obj_relocate (struct obj_file *f, ElfW(Addr) base); +static int obj_relocate(struct obj_file *f, ElfW(Addr) base); static struct obj_file *obj_load(FILE *f, int loadprogbits); -static int obj_create_image (struct obj_file *f, char *image); +static int obj_create_image(struct obj_file *f, char *image); /* Architecture specific manipulation routines. */ -static struct obj_file *arch_new_file (void); +static struct obj_file *arch_new_file(void); -static struct obj_section *arch_new_section (void); +static struct obj_section *arch_new_section(void); -static struct obj_symbol *arch_new_symbol (void); +static struct obj_symbol *arch_new_symbol(void); -static enum obj_reloc arch_apply_relocation (struct obj_file *f, +static enum obj_reloc arch_apply_relocation(struct obj_file *f, struct obj_section *targsec, struct obj_section *symsec, struct obj_symbol *sym, ElfW(RelM) *rel, ElfW(Addr) value); -static void arch_create_got (struct obj_file *f); +static void arch_create_got(struct obj_file *f); #if ENABLE_FEATURE_CHECK_TAINTED_MODULE static int obj_gpl_license(struct obj_file *f, const char **license); -#endif /* ENABLE_FEATURE_CHECK_TAINTED_MODULE */ +#endif /* FEATURE_CHECK_TAINTED_MODULE */ #endif /* obj.h */ //---------------------------------------------------------------------------- //--------end of modutils obj.h @@ -681,7 +678,7 @@ static int obj_gpl_license(struct obj_file *f, const char **license); #define _PATH_MODULES "/lib/modules" -enum { STRVERSIONLEN = 32 }; +enum { STRVERSIONLEN = 64 }; /*======================================================================*/ @@ -709,7 +706,7 @@ enum { #define flag_verbose (option_mask32 & OPT_v) #define flag_quiet (option_mask32 & OPT_q) #define flag_noexport (option_mask32 & OPT_x) -#ifdef CONFIG_FEATURE_INSMOD_LOAD_MAP +#if ENABLE_FEATURE_INSMOD_LOAD_MAP #define flag_print_load_map (option_mask32 & OPT_m) #else #define flag_print_load_map 0 @@ -717,19 +714,19 @@ enum { /*======================================================================*/ -#if defined(CONFIG_USE_LIST) +#if defined(USE_LIST) struct arch_list_entry { struct arch_list_entry *next; - CONFIG_LIST_ARCHTYPE addend; + LIST_ARCHTYPE addend; int offset; int inited : 1; }; #endif -#if defined(CONFIG_USE_SINGLE) +#if defined(USE_SINGLE) struct arch_single_entry { @@ -751,10 +748,10 @@ struct mips_hi16 struct arch_file { struct obj_file root; -#if defined(CONFIG_USE_PLT_ENTRIES) +#if defined(USE_PLT_ENTRIES) struct obj_section *plt; #endif -#if defined(CONFIG_USE_GOT_ENTRIES) +#if defined(USE_GOT_ENTRIES) struct obj_section *got; #endif #if defined(__mips__) @@ -764,14 +761,14 @@ struct arch_file { struct arch_symbol { struct obj_symbol root; -#if defined(CONFIG_USE_PLT_ENTRIES) -#if defined(CONFIG_USE_PLT_LIST) +#if defined(USE_PLT_ENTRIES) +#if defined(USE_PLT_LIST) struct arch_list_entry *pltent; #else struct arch_single_entry pltent; #endif #endif -#if defined(CONFIG_USE_GOT_ENTRIES) +#if defined(USE_GOT_ENTRIES) struct arch_single_entry gotent; #endif }; @@ -801,24 +798,24 @@ static char *m_fullName; static int check_module_name_match(const char *filename, struct stat *statbuf, - void *userdata) + void *userdata, int depth) { char *fullname = (char *) userdata; if (fullname[0] == '\0') - return (FALSE); + return FALSE; else { char *tmp, *tmp1 = xstrdup(filename); - tmp = bb_get_last_path_component(tmp1); + tmp = bb_get_last_path_component_nostrip(tmp1); if (strcmp(tmp, fullname) == 0) { free(tmp1); /* Stop searching if we find a match */ m_filename = xstrdup(filename); - return (FALSE); + return FALSE; } free(tmp1); } - return (TRUE); + return TRUE; } @@ -860,18 +857,18 @@ arch_apply_relocation(struct obj_file *f, enum obj_reloc ret = obj_reloc_ok; ElfW(Addr) *loc = (ElfW(Addr) *) (targsec->contents + rel->r_offset); ElfW(Addr) dot = targsec->header.sh_addr + rel->r_offset; -#if defined(CONFIG_USE_GOT_ENTRIES) || defined(CONFIG_USE_PLT_ENTRIES) +#if defined(USE_GOT_ENTRIES) || defined(USE_PLT_ENTRIES) struct arch_symbol *isym = (struct arch_symbol *) sym; #endif #if defined(__arm__) || defined(__i386__) || defined(__mc68000__) || defined(__sh__) || defined(__s390__) -#if defined(CONFIG_USE_GOT_ENTRIES) +#if defined(USE_GOT_ENTRIES) ElfW(Addr) got = ifile->got ? ifile->got->header.sh_addr : 0; #endif #endif -#if defined(CONFIG_USE_PLT_ENTRIES) +#if defined(USE_PLT_ENTRIES) ElfW(Addr) plt = ifile->plt ? ifile->plt->header.sh_addr : 0; unsigned long *ip; -# if defined(CONFIG_USE_PLT_LIST) +# if defined(USE_PLT_LIST) struct arch_list_entry *pe; # else struct arch_single_entry *pe; @@ -984,7 +981,7 @@ arch_apply_relocation(struct obj_file *f, *loc += v - got; break; -#elif defined (__microblaze__) +#elif defined(__microblaze__) case R_MICROBLAZE_NONE: case R_MICROBLAZE_64_NONE: case R_MICROBLAZE_32_SYM_OP_SYM: @@ -1132,7 +1129,7 @@ arch_apply_relocation(struct obj_file *f, /* We cannot relocate this one now because we don't know the value of the carry we need to add. Save the information, and let LO16 do the actual relocation. */ - n = (struct mips_hi16 *) xmalloc(sizeof *n); + n = xmalloc(sizeof *n); n->addr = loc; n->value = v; n->next = ifile->mips_hi16_list; @@ -1542,7 +1539,7 @@ arch_apply_relocation(struct obj_file *f, } # endif /* __SH5__ */ -#elif defined (__v850e__) +#elif defined(__v850e__) case R_V850_NONE: break; @@ -1637,13 +1634,13 @@ arch_apply_relocation(struct obj_file *f, ret = obj_reloc_unhandled; break; -#if defined(CONFIG_USE_PLT_ENTRIES) +#if defined(USE_PLT_ENTRIES) bb_use_plt: /* find the plt entry and initialize it if necessary */ -#if defined(CONFIG_USE_PLT_LIST) +#if defined(USE_PLT_LIST) for (pe = isym->pltent; pe != NULL && pe->addend != rel->r_addend;) pe = pe->next; #else @@ -1665,7 +1662,7 @@ bb_use_plt: ip[2] = 0x7d6903a6; /* mtctr r11 */ ip[3] = 0x4e800420; /* bctr */ #endif -#if defined (__v850e__) +#if defined(__v850e__) /* We have to trash a register, so we assume that any control transfer more than 21-bits away must be a function call (so we can use a call-clobbered register). */ @@ -1678,15 +1675,15 @@ bb_use_plt: /* relative distance to target */ v -= dot; /* if the target is too far away.... */ -#if defined (__arm__) || defined (__powerpc__) +#if defined(__arm__) || defined(__powerpc__) if ((int)v < -0x02000000 || (int)v >= 0x02000000) -#elif defined (__v850e__) +#elif defined(__v850e__) if ((ElfW(Sword))v > 0x1fffff || (ElfW(Sword))v < (ElfW(Sword))-0x200000) #endif /* go via the plt */ v = plt + pe->offset - dot; -#if defined (__v850e__) +#if defined(__v850e__) if (v & 1) #else if (v & 3) @@ -1703,7 +1700,7 @@ bb_use_plt: #if defined(__powerpc__) *loc = (*loc & ~0x03fffffc) | (v & 0x03fffffc); #endif -#if defined (__v850e__) +#if defined(__v850e__) /* We write two shorts instead of a long because even 32-bit insns only need half-word alignment, but the 32-bit data write needs to be long-word aligned. */ @@ -1714,9 +1711,9 @@ bb_use_plt: (v & 0xffff); /* offs low part */ #endif break; -#endif /* CONFIG_USE_PLT_ENTRIES */ +#endif /* USE_PLT_ENTRIES */ -#if defined(CONFIG_USE_GOT_ENTRIES) +#if defined(USE_GOT_ENTRIES) bb_use_got: /* needs an entry in the .got: set it, once */ @@ -1732,14 +1729,14 @@ bb_use_got: #endif break; -#endif /* CONFIG_USE_GOT_ENTRIES */ +#endif /* USE_GOT_ENTRIES */ } return ret; } -#if defined(CONFIG_USE_LIST) +#if defined(USE_LIST) static int arch_list_add(ElfW(RelM) *rel, struct arch_list_entry **list, int offset, int size) @@ -1766,7 +1763,7 @@ static int arch_list_add(ElfW(RelM) *rel, struct arch_list_entry **list, #endif -#if defined(CONFIG_USE_SINGLE) +#if defined(USE_SINGLE) static int arch_single_init(ElfW(RelM) *rel, struct arch_single_entry *single, int offset, int size) @@ -1782,9 +1779,9 @@ static int arch_single_init(ElfW(RelM) *rel, struct arch_single_entry *single, #endif -#if defined(CONFIG_USE_GOT_ENTRIES) || defined(CONFIG_USE_PLT_ENTRIES) +#if defined(USE_GOT_ENTRIES) || defined(USE_PLT_ENTRIES) -static struct obj_section *arch_xsect_init(struct obj_file *f, char *name, +static struct obj_section *arch_xsect_init(struct obj_file *f, const char *name, int offset, int size) { struct obj_section *myrelsec = obj_find_section(f, name); @@ -1807,13 +1804,13 @@ static struct obj_section *arch_xsect_init(struct obj_file *f, char *name, static void arch_create_got(struct obj_file *f) { -#if defined(CONFIG_USE_GOT_ENTRIES) || defined(CONFIG_USE_PLT_ENTRIES) +#if defined(USE_GOT_ENTRIES) || defined(USE_PLT_ENTRIES) struct arch_file *ifile = (struct arch_file *) f; int i; -#if defined(CONFIG_USE_GOT_ENTRIES) +#if defined(USE_GOT_ENTRIES) int got_offset = 0, got_needed = 0, got_allocate; #endif -#if defined(CONFIG_USE_PLT_ENTRIES) +#if defined(USE_PLT_ENTRIES) int plt_offset = 0, plt_needed = 0, plt_allocate; #endif struct obj_section *relsec, *symsec, *strsec; @@ -1838,10 +1835,10 @@ static void arch_create_got(struct obj_file *f) for (; rel < relend; ++rel) { extsym = &symtab[ELF_R_SYM(rel->r_info)]; -#if defined(CONFIG_USE_GOT_ENTRIES) +#if defined(USE_GOT_ENTRIES) got_allocate = 0; #endif -#if defined(CONFIG_USE_PLT_ENTRIES) +#if defined(USE_PLT_ENTRIES) plt_allocate = 0; #endif @@ -1897,7 +1894,7 @@ static void arch_create_got(struct obj_file *f) got_needed = 1; continue; -#elif defined (__v850e__) +#elif defined(__v850e__) case R_V850_22_PCREL: plt_needed = 1; break; @@ -1913,25 +1910,25 @@ static void arch_create_got(struct obj_file *f) name = f->sections[extsym->st_shndx]->name; } intsym = (struct arch_symbol *) obj_find_symbol(f, name); -#if defined(CONFIG_USE_GOT_ENTRIES) +#if defined(USE_GOT_ENTRIES) if (got_allocate) { got_offset += arch_single_init( rel, &intsym->gotent, - got_offset, CONFIG_GOT_ENTRY_SIZE); + got_offset, GOT_ENTRY_SIZE); got_needed = 1; } #endif -#if defined(CONFIG_USE_PLT_ENTRIES) +#if defined(USE_PLT_ENTRIES) if (plt_allocate) { -#if defined(CONFIG_USE_PLT_LIST) +#if defined(USE_PLT_LIST) plt_offset += arch_list_add( rel, &intsym->pltent, - plt_offset, CONFIG_PLT_ENTRY_SIZE); + plt_offset, PLT_ENTRY_SIZE); #else plt_offset += arch_single_init( rel, &intsym->pltent, - plt_offset, CONFIG_PLT_ENTRY_SIZE); + plt_offset, PLT_ENTRY_SIZE); #endif plt_needed = 1; } @@ -1939,21 +1936,21 @@ static void arch_create_got(struct obj_file *f) } } -#if defined(CONFIG_USE_GOT_ENTRIES) +#if defined(USE_GOT_ENTRIES) if (got_needed) { ifile->got = arch_xsect_init(f, ".got", got_offset, - CONFIG_GOT_ENTRY_SIZE); + GOT_ENTRY_SIZE); } #endif -#if defined(CONFIG_USE_PLT_ENTRIES) +#if defined(USE_PLT_ENTRIES) if (plt_needed) { ifile->plt = arch_xsect_init(f, ".plt", plt_offset, - CONFIG_PLT_ENTRY_SIZE); + PLT_ENTRY_SIZE); } #endif -#endif /* defined(CONFIG_USE_GOT_ENTRIES) || defined(CONFIG_USE_PLT_ENTRIES) */ +#endif /* defined(USE_GOT_ENTRIES) || defined(USE_PLT_ENTRIES) */ } /*======================================================================*/ @@ -1982,7 +1979,7 @@ static unsigned long obj_elf_hash(const char *name) return obj_elf_hash_n(name, strlen(name)); } -#ifdef CONFIG_FEATURE_INSMOD_VERSION_CHECKING +#if ENABLE_FEATURE_INSMOD_VERSION_CHECKING /* String comparison for non-co-versioned kernel and module. */ static int ncv_strcmp(const char *a, const char *b) @@ -2034,7 +2031,7 @@ obj_set_symbol_compare(struct obj_file *f, } } -#endif /* CONFIG_FEATURE_INSMOD_VERSION_CHECKING */ +#endif /* FEATURE_INSMOD_VERSION_CHECKING */ static struct obj_symbol * obj_add_symbol(struct obj_file *f, const char *name, @@ -2281,7 +2278,7 @@ add_symbols_from( struct obj_file *f, char *name_buf = 0; size_t name_alloced_size = 0; #endif -#ifdef CONFIG_FEATURE_CHECK_TAINTED_MODULE +#if ENABLE_FEATURE_CHECK_TAINTED_MODULE int gpl; gpl = obj_gpl_license(f, NULL) == 0; @@ -2301,7 +2298,7 @@ add_symbols_from( struct obj_file *f, * their references. */ if (strncmp((char *)s->name, "GPLONLY_", 8) == 0) { -#ifdef CONFIG_FEATURE_CHECK_TAINTED_MODULE +#if ENABLE_FEATURE_CHECK_TAINTED_MODULE if (gpl) s->name += 8; else @@ -2315,13 +2312,13 @@ add_symbols_from( struct obj_file *f, kernel exports `C names', but module object files reference `linker names'). */ size_t extra = sizeof SYMBOL_PREFIX; - size_t name_size = strlen (name) + extra; + size_t name_size = strlen(name) + extra; if (name_size > name_alloced_size) { name_alloced_size = name_size * 2; - name_buf = alloca (name_alloced_size); + name_buf = alloca(name_alloced_size); } - strcpy (name_buf, SYMBOL_PREFIX); - strcpy (name_buf + extra - 1, name); + strcpy(name_buf, SYMBOL_PREFIX); + strcpy(name_buf + extra - 1, name); name = name_buf; #endif /* SYMBOL_PREFIX */ @@ -2329,8 +2326,8 @@ add_symbols_from( struct obj_file *f, if (sym && !(ELF_ST_BIND(sym->info) == STB_LOCAL)) { #ifdef SYMBOL_PREFIX /* Put NAME_BUF into more permanent storage. */ - name = xmalloc (name_size); - strcpy (name, name_buf); + name = xmalloc(name_size); + strcpy(name, name_buf); #endif sym = obj_add_symbol(f, name, -1, ELF_ST_INFO(STB_GLOBAL, @@ -2353,10 +2350,14 @@ static void add_kernel_symbols(struct obj_file *f) /* Add module symbols first. */ - for (i = 0, m = ext_modules; i < n_ext_modules; ++i, ++m) + for (i = 0, m = ext_modules; i < n_ext_modules; ++i, ++m) { if (m->nsyms - && add_symbols_from(f, SHN_HIRESERVE + 2 + i, m->syms, - m->nsyms)) m->used = 1, ++nused; + && add_symbols_from(f, SHN_HIRESERVE + 2 + i, m->syms, m->nsyms) + ) { + m->used = 1; + ++nused; + } + } n_ext_modules_used = nused; @@ -2425,9 +2426,9 @@ new_process_module_arguments(struct obj_file *f, int argc, char **argv) } #ifdef SYMBOL_PREFIX - sym_name = alloca (strlen (key) + sizeof SYMBOL_PREFIX); - strcpy (sym_name, SYMBOL_PREFIX); - strcat (sym_name, key); + sym_name = alloca(strlen(key) + sizeof SYMBOL_PREFIX); + strcpy(sym_name, SYMBOL_PREFIX); + strcat(sym_name, key); #else sym_name = key; #endif @@ -2542,7 +2543,7 @@ new_process_module_arguments(struct obj_file *f, int argc, char **argv) } else { /* last string */ str = q; - q = ""; + q = (char*)""; } } @@ -2551,7 +2552,7 @@ new_process_module_arguments(struct obj_file *f, int argc, char **argv) obj_string_patch(f, sym->secidx, loc - contents, str); loc += tgt_sizeof_char_p; } else { - /* Array of chars (in fact, matrix !) */ + /* Array of chars (in fact, matrix!) */ unsigned long charssize; /* size of each member */ /* Get the size of each member */ @@ -2637,7 +2638,7 @@ end_of_arg: return 1; } -#ifdef CONFIG_FEATURE_INSMOD_VERSION_CHECKING +#if ENABLE_FEATURE_INSMOD_VERSION_CHECKING static int new_is_module_checksummed(struct obj_file *f) { const char *p = get_modinfo_value(f, "using_checksums"); @@ -2673,7 +2674,7 @@ new_get_module_version(struct obj_file *f, char str[STRVERSIONLEN]) return a << 16 | b << 8 | c; } -#endif /* CONFIG_FEATURE_INSMOD_VERSION_CHECKING */ +#endif /* FEATURE_INSMOD_VERSION_CHECKING */ /* Fetch the loaded modules, and all currently exported symbols. */ @@ -2803,7 +2804,7 @@ static int new_create_this_module(struct obj_file *f, const char *m_name) return 1; } -#ifdef CONFIG_FEATURE_INSMOD_KSYMOOPS_SYMBOLS +#if ENABLE_FEATURE_INSMOD_KSYMOOPS_SYMBOLS /* add an entry to the __ksymtab section, creating it if necessary */ static void new_add_ksymtab(struct obj_file *f, struct obj_symbol *sym) { @@ -2826,14 +2827,14 @@ static void new_add_ksymtab(struct obj_file *f, struct obj_symbol *sym) if (!sec) return; sec->header.sh_flags |= SHF_ALLOC; - sec->header.sh_addralign = tgt_sizeof_void_p; /* Empty section might - be byte-aligned */ + /* Empty section might be byte-aligned */ + sec->header.sh_addralign = tgt_sizeof_void_p; ofs = sec->header.sh_size; obj_symbol_patch(f, sec->idx, ofs, sym); obj_string_patch(f, sec->idx, ofs + tgt_sizeof_void_p, sym->name); obj_extend_section(sec, 2 * tgt_sizeof_char_p); } -#endif /* CONFIG_FEATURE_INSMOD_KSYMOOPS_SYMBOLS */ +#endif /* FEATURE_INSMOD_KSYMOOPS_SYMBOLS */ static int new_create_module_ksymtab(struct obj_file *f) { @@ -3408,7 +3409,7 @@ static struct obj_file *obj_load(FILE * fp, int loadprogbits) sec->header = section_headers[i]; sec->idx = i; - if(sec->header.sh_size) { + if (sec->header.sh_size) { switch (sec->header.sh_type) { case SHT_NULL: case SHT_NOTE: @@ -3552,7 +3553,7 @@ static struct obj_file *obj_load(FILE * fp, int loadprogbits) return f; } -#ifdef CONFIG_FEATURE_INSMOD_LOADINKMEM +#if ENABLE_FEATURE_INSMOD_LOADINKMEM /* * load the unloaded sections directly into the memory allocated by * kernel for the module @@ -3604,7 +3605,7 @@ static void hide_special_symbols(struct obj_file *f) } -#ifdef CONFIG_FEATURE_CHECK_TAINTED_MODULE +#if ENABLE_FEATURE_CHECK_TAINTED_MODULE static int obj_gpl_license(struct obj_file *f, const char **license) { struct obj_section *sec; @@ -3612,12 +3613,12 @@ static int obj_gpl_license(struct obj_file *f, const char **license) * linux/include/linux/module.h. Checking for leading "GPL" will not * work, somebody will use "GPL sucks, this is proprietary". */ - static const char * const gpl_licenses[] = { + static const char *const gpl_licenses[] = { "GPL", "GPL v2", "GPL and additional rights", "Dual BSD/GPL", - "Dual MPL/GPL", + "Dual MPL/GPL" }; sec = obj_find_section(f, ".modinfo"); @@ -3631,11 +3632,11 @@ static int obj_gpl_license(struct obj_file *f, const char **license) int i; if (license) *license = value+1; - for (i = 0; i < sizeof(gpl_licenses)/sizeof(gpl_licenses[0]); ++i) { + for (i = 0; i < ARRAY_SIZE(gpl_licenses); ++i) { if (strcmp(value+1, gpl_licenses[i]) == 0) - return(0); + return 0; } - return(2); + return 2; } if (strchr(ptr, '\0')) ptr = strchr(ptr, '\0') + 1; @@ -3643,7 +3644,7 @@ static int obj_gpl_license(struct obj_file *f, const char **license) ptr = endptr; } } - return(1); + return 1; } #define TAINT_FILENAME "/proc/sys/kernel/tainted" @@ -3655,16 +3656,18 @@ static int obj_gpl_license(struct obj_file *f, const char **license) static void set_tainted(struct obj_file *f, int fd, char *m_name, int kernel_has_tainted, int taint, const char *text1, const char *text2) { + static smallint printed_info; + char buf[80]; int oldval; - static int first = 1; + if (fd < 0 && !kernel_has_tainted) return; /* New modutils on old kernel */ printf("Warning: loading %s will taint the kernel: %s%s\n", m_name, text1, text2); - if (first) { + if (!printed_info) { printf(" See %s for information about tainted modules\n", TAINT_URL); - first = 0; + printed_info = 1; } if (fd >= 0) { read(fd, buf, sizeof(buf)-1); @@ -3678,7 +3681,8 @@ static void set_tainted(struct obj_file *f, int fd, char *m_name, /* Check if loading this module will taint the kernel. */ static void check_tainted_module(struct obj_file *f, char *m_name) { - static const char tainted_file[] = TAINT_FILENAME; + static const char tainted_file[] ALIGN1 = TAINT_FILENAME; + int fd, kernel_has_tainted; const char *ptr; @@ -3719,11 +3723,11 @@ static void check_tainted_module(struct obj_file *f, char *m_name) if (fd >= 0) close(fd); } -#else /* CONFIG_FEATURE_CHECK_TAINTED_MODULE */ -#define check_tainted_module(x, y) do { } while(0); -#endif /* CONFIG_FEATURE_CHECK_TAINTED_MODULE */ +#else /* FEATURE_CHECK_TAINTED_MODULE */ +#define check_tainted_module(x, y) do { } while (0); +#endif /* FEATURE_CHECK_TAINTED_MODULE */ -#ifdef CONFIG_FEATURE_INSMOD_KSYMOOPS_SYMBOLS +#if ENABLE_FEATURE_INSMOD_KSYMOOPS_SYMBOLS /* add module source, timestamp, kernel version and a symbol for the * start of some sections. this info is used by ksymoops to do better * debugging. @@ -3731,12 +3735,12 @@ static void check_tainted_module(struct obj_file *f, char *m_name) static int get_module_version(struct obj_file *f, char str[STRVERSIONLEN]) { -#ifdef CONFIG_FEATURE_INSMOD_VERSION_CHECKING +#if ENABLE_FEATURE_INSMOD_VERSION_CHECKING return new_get_module_version(f, str); -#else /* CONFIG_FEATURE_INSMOD_VERSION_CHECKING */ +#else /* FEATURE_INSMOD_VERSION_CHECKING */ strncpy(str, "???", sizeof(str)); return -1; -#endif /* CONFIG_FEATURE_INSMOD_VERSION_CHECKING */ +#endif /* FEATURE_INSMOD_VERSION_CHECKING */ } /* add module source, timestamp, kernel version and a symbol for the @@ -3747,7 +3751,8 @@ static void add_ksymoops_symbols(struct obj_file *f, const char *filename, const char *m_name) { - static const char symprefix[] = "__insmod_"; + static const char symprefix[] ALIGN1 = "__insmod_"; + struct obj_section *sec; struct obj_symbol *sym; char *name, *absolute_filename; @@ -3765,12 +3770,8 @@ add_ksymoops_symbols(struct obj_file *f, const char *filename, if (realpath(filename, real)) { absolute_filename = xstrdup(real); - } - else { - int save_errno = errno; - bb_error_msg("cannot get realpath for %s", filename); - errno = save_errno; - perror(""); + } else { + bb_perror_msg("cannot get realpath for %s", filename); absolute_filename = xstrdup(filename); } @@ -3783,7 +3784,8 @@ add_ksymoops_symbols(struct obj_file *f, const char *filename, */ use_ksymtab = obj_find_section(f, "__ksymtab") || flag_noexport; - if ((sec = obj_find_section(f, ".this"))) { + sec = obj_find_section(f, ".this"); + if (sec) { /* tag the module header with the object name, last modified * timestamp and module version. worst case for module version * is 0xffffff, decimal 16777215. putting all three fields in @@ -3833,9 +3835,9 @@ add_ksymoops_symbols(struct obj_file *f, const char *filename, #endif /* _NOT_SUPPORTED_ */ /* tag the desired sections if size is non-zero */ - for (i = 0; i < sizeof(section_names)/sizeof(section_names[0]); ++i) { - if ((sec = obj_find_section(f, section_names[i])) && - sec->header.sh_size) { + for (i = 0; i < ARRAY_SIZE(section_names); ++i) { + sec = obj_find_section(f, section_names[i]); + if (sec && sec->header.sh_size) { l = sizeof(symprefix)+ /* "__insmod_" */ lm_name+ /* module name */ 2+ /* "_S" */ @@ -3854,16 +3856,17 @@ add_ksymoops_symbols(struct obj_file *f, const char *filename, } } } -#endif /* CONFIG_FEATURE_INSMOD_KSYMOOPS_SYMBOLS */ +#endif /* FEATURE_INSMOD_KSYMOOPS_SYMBOLS */ -#ifdef CONFIG_FEATURE_INSMOD_LOAD_MAP +#if ENABLE_FEATURE_INSMOD_LOAD_MAP static void print_load_map(struct obj_file *f) { - struct obj_symbol *sym; - struct obj_symbol **all, **p; struct obj_section *sec; +#if ENABLE_FEATURE_INSMOD_LOAD_MAP_FULL + struct obj_symbol **all, **p; int i, nsyms, *loaded; - + struct obj_symbol *sym; +#endif /* Report on the section layout. */ printf("Sections: Size %-*s Align\n", @@ -3885,7 +3888,7 @@ static void print_load_map(struct obj_file *f) (long)sec->header.sh_addr, a); } -#ifdef CONFIG_FEATURE_INSMOD_LOAD_MAP_FULL +#if ENABLE_FEATURE_INSMOD_LOAD_MAP_FULL /* Quick reference which section indicies are loaded. */ loaded = alloca(sizeof(int) * (i = f->header.e_shnum)); @@ -3945,11 +3948,12 @@ static void print_load_map(struct obj_file *f) } #endif } -#else /* !CONFIG_FEATURE_INSMOD_LOAD_MAP */ +#else /* !FEATURE_INSMOD_LOAD_MAP */ void print_load_map(struct obj_file *f); #endif -int insmod_main( int argc, char **argv) +int insmod_main(int argc, char **argv) MAIN_EXTERNALLY_VISIBLE; +int insmod_main(int argc, char **argv) { char *opt_o, *arg1; int len; @@ -3962,13 +3966,13 @@ int insmod_main( int argc, char **argv) char *m_name = 0; int exit_status = EXIT_FAILURE; int m_has_modinfo; -#ifdef CONFIG_FEATURE_INSMOD_VERSION_CHECKING +#if ENABLE_FEATURE_INSMOD_VERSION_CHECKING struct utsname uts_info; char m_strversion[STRVERSIONLEN]; int m_version, m_crcs; #endif -#ifdef CONFIG_FEATURE_CLEAN_UP - FILE *fp = 0; +#if ENABLE_FEATURE_CLEAN_UP + FILE *fp = NULL; #else FILE *fp; #endif @@ -3976,7 +3980,7 @@ int insmod_main( int argc, char **argv) struct utsname myuname; /* Parse any options */ - getopt32(argc, argv, OPTION_STR, &opt_o); + getopt32(argv, OPTION_STR, &opt_o); arg1 = argv[optind]; if (option_mask32 & OPT_o) { // -o /* name the output module */ free(m_name); @@ -3998,7 +4002,7 @@ int insmod_main( int argc, char **argv) } } -#if defined(CONFIG_FEATURE_2_6_MODULES) +#if ENABLE_FEATURE_2_6_MODULES if (k_version > 4 && len > 3 && tmp[len - 3] == '.' && tmp[len - 2] == 'k' && tmp[len - 1] == 'o' ) { @@ -4012,7 +4016,7 @@ int insmod_main( int argc, char **argv) } -#if defined(CONFIG_FEATURE_2_6_MODULES) +#if ENABLE_FEATURE_2_6_MODULES if (k_version > 4) m_fullName = xasprintf("%s.ko", tmp); else @@ -4026,7 +4030,7 @@ int insmod_main( int argc, char **argv) tmp1 = 0; /* flag for free(m_name) before exit() */ } - /* Get a filedesc for the module. Check we we have a complete path */ + /* Get a filedesc for the module. Check that we have a complete path */ if (stat(arg1, &st) < 0 || !S_ISREG(st.st_mode) || (fp = fopen(arg1, "r")) == NULL ) { @@ -4047,32 +4051,32 @@ int insmod_main( int argc, char **argv) module_dir = tmdn; else module_dir = real_module_dir; - recursive_action(module_dir, TRUE, FALSE, FALSE, - check_module_name_match, 0, m_fullName); + recursive_action(module_dir, ACTION_RECURSE, + check_module_name_match, 0, m_fullName, 0); free(tmdn); } /* Check if we have found anything yet */ - if (m_filename == 0 || ((fp = fopen(m_filename, "r")) == NULL)) { + if (!m_filename || ((fp = fopen(m_filename, "r")) == NULL)) { char module_dir[FILENAME_MAX]; free(m_filename); - m_filename = 0; - if (realpath (_PATH_MODULES, module_dir) == NULL) + m_filename = NULL; + if (realpath(_PATH_MODULES, module_dir) == NULL) strcpy(module_dir, _PATH_MODULES); /* No module found under /lib/modules/`uname -r`, this * time cast the net a bit wider. Search /lib/modules/ */ - if (!recursive_action(module_dir, TRUE, FALSE, FALSE, - check_module_name_match, 0, m_fullName) + if (!recursive_action(module_dir, ACTION_RECURSE, + check_module_name_match, 0, m_fullName, 0) ) { if (m_filename == 0 || ((fp = fopen(m_filename, "r")) == NULL) ) { - bb_error_msg("%s: no module by that name found", m_fullName); + bb_error_msg("%s: module not found", m_fullName); goto out; } } else - bb_error_msg_and_die("%s: no module by that name found", m_fullName); + bb_error_msg_and_die("%s: module not found", m_fullName); } } else m_filename = xstrdup(arg1); @@ -4080,7 +4084,7 @@ int insmod_main( int argc, char **argv) if (flag_verbose) printf("Using %s\n", m_filename); -#ifdef CONFIG_FEATURE_2_6_MODULES +#if ENABLE_FEATURE_2_6_MODULES if (k_version > 4) { argv[optind] = m_filename; optind--; @@ -4097,7 +4101,7 @@ int insmod_main( int argc, char **argv) else m_has_modinfo = 1; -#ifdef CONFIG_FEATURE_INSMOD_VERSION_CHECKING +#if ENABLE_FEATURE_INSMOD_VERSION_CHECKING /* Version correspondence? */ if (!flag_quiet) { if (uname(&uts_info) < 0) @@ -4112,40 +4116,35 @@ int insmod_main( int argc, char **argv) } if (strncmp(uts_info.release, m_strversion, STRVERSIONLEN) != 0) { - if (flag_force_load) { - bb_error_msg("Warning: kernel-module version mismatch\n" - "\t%s was compiled for kernel version %s\n" - "\twhile this kernel is version %s", - m_filename, m_strversion, uts_info.release); - } else { - bb_error_msg("kernel-module version mismatch\n" - "\t%s was compiled for kernel version %s\n" - "\twhile this kernel is version %s.", - m_filename, m_strversion, uts_info.release); + bb_error_msg("%skernel-module version mismatch\n" + "\t%s was compiled for kernel version %s\n" + "\twhile this kernel is version %s", + flag_force_load ? "warning: " : "", + m_filename, m_strversion, uts_info.release); + if (!flag_force_load) goto out; - } } } k_crcs = 0; -#endif /* CONFIG_FEATURE_INSMOD_VERSION_CHECKING */ +#endif /* FEATURE_INSMOD_VERSION_CHECKING */ if (!query_module(NULL, 0, NULL, 0, NULL)) { if (!new_get_kernel_symbols()) goto out; k_crcs = new_is_kernel_checksummed(); } else { - bb_error_msg("Not configured to support old kernels"); + bb_error_msg("not configured to support old kernels"); goto out; } -#ifdef CONFIG_FEATURE_INSMOD_VERSION_CHECKING +#if ENABLE_FEATURE_INSMOD_VERSION_CHECKING m_crcs = 0; if (m_has_modinfo) m_crcs = new_is_module_checksummed(f); if (m_crcs != k_crcs) obj_set_symbol_compare(f, ncv_strcmp, ncv_symbol_hash); -#endif /* CONFIG_FEATURE_INSMOD_VERSION_CHECKING */ +#endif /* FEATURE_INSMOD_VERSION_CHECKING */ /* Let the module know about the kernel symbols. */ add_kernel_symbols(f); @@ -4173,9 +4172,9 @@ int insmod_main( int argc, char **argv) arch_create_got(f); hide_special_symbols(f); -#ifdef CONFIG_FEATURE_INSMOD_KSYMOOPS_SYMBOLS +#if ENABLE_FEATURE_INSMOD_KSYMOOPS_SYMBOLS add_ksymoops_symbols(f, m_filename, m_name); -#endif /* CONFIG_FEATURE_INSMOD_KSYMOOPS_SYMBOLS */ +#endif /* FEATURE_INSMOD_KSYMOOPS_SYMBOLS */ new_create_module_ksymtab(f); @@ -4218,29 +4217,28 @@ int insmod_main( int argc, char **argv) goto out; } - if(flag_print_load_map) + if (flag_print_load_map) print_load_map(f); exit_status = EXIT_SUCCESS; out: -#ifdef CONFIG_FEATURE_CLEAN_UP - if(fp) +#if ENABLE_FEATURE_CLEAN_UP + if (fp) fclose(fp); free(tmp1); - if(!tmp1) { + if (!tmp1) free(m_name); - } free(m_filename); #endif - return(exit_status); + return exit_status; } #endif -#ifdef CONFIG_FEATURE_2_6_MODULES +#if ENABLE_FEATURE_2_6_MODULES #include #include @@ -4263,48 +4261,54 @@ static const char *moderror(int err) } } -int insmod_ng_main( int argc, char **argv) +int insmod_ng_main(int argc, char **argv) MAIN_EXTERNALLY_VISIBLE; +int insmod_ng_main(int argc, char **argv) { - int i; - int fd; - long int ret; - struct stat st; - unsigned long len; + long ret; + size_t len; + int optlen; void *map; - char *filename, *options = xstrdup(""); + char *filename, *options; - filename = argv[1]; - if (!filename) { + filename = *++argv; + if (!filename) bb_show_usage(); - return -1; - } /* Rest is options */ - for (i = 2; i < argc; i++) { - options = xrealloc(options, strlen(options) + 2 + strlen(argv[i]) + 2); + options = xzalloc(1); + optlen = 0; + while (*++argv) { + options = xrealloc(options, optlen + 2 + strlen(*argv) + 2); /* Spaces handled by "" pairs, but no way of escaping quotes */ - if (strchr(argv[i], ' ')) { - strcat(options, "\""); - strcat(options, argv[i]); - strcat(options, "\""); - } else { - strcat(options, argv[i]); - } - strcat(options, " "); + optlen += sprintf(options + optlen, (strchr(*argv,' ') ? "\"%s\" " : "%s "), *argv); } +#if 0 + /* Any special reason why mmap? It isn't performace critical... */ + int fd; + struct stat st; + unsigned long len; fd = xopen(filename, O_RDONLY); - fstat(fd, &st); len = st.st_size; map = mmap(NULL, len, PROT_READ, MAP_PRIVATE, fd, 0); if (map == MAP_FAILED) { - bb_perror_msg_and_die("cannot mmap `%s'", filename); + bb_perror_msg_and_die("cannot mmap '%s'", filename); + } + + /* map == NULL on Blackfin, probably on other MMU-less systems too. Workaround. */ + if (map == NULL) { + map = xmalloc(len); + xread(fd, map, len); } +#else + len = MAXINT(ssize_t); + map = xmalloc_open_read_close(filename, &len); +#endif ret = syscall(__NR_init_module, map, len, options); if (ret != 0) { - bb_perror_msg_and_die("cannot insert `%s': %s (%li)", + bb_perror_msg_and_die("cannot insert '%s': %s (%li)", filename, moderror(errno), ret); }