diff options
| author | vda <vda@69ca8d6d-28ef-0310-b511-8ec308f3f277> | 2006-10-12 20:06:18 +0000 |
|---|---|---|
| committer | vda <vda@69ca8d6d-28ef-0310-b511-8ec308f3f277> | 2006-10-12 20:06:18 +0000 |
| commit | 008062af2e92cc171a79b2682e40cf092d6fe653 (patch) | |
| tree | c238cf9dfb9933506f7067011ac696794df1906a /modutils | |
| parent | da4602016b3e8cdedf055050ffef85c61c9f60ca (diff) | |
| download | busybox-w32-008062af2e92cc171a79b2682e40cf092d6fe653.tar.gz busybox-w32-008062af2e92cc171a79b2682e40cf092d6fe653.tar.bz2 busybox-w32-008062af2e92cc171a79b2682e40cf092d6fe653.zip | |
style fixes
git-svn-id: svn://busybox.net/trunk/busybox@16373 69ca8d6d-28ef-0310-b511-8ec308f3f277
Diffstat (limited to 'modutils')
| -rw-r--r-- | modutils/insmod.c | 551 |
1 files changed, 271 insertions, 280 deletions
diff --git a/modutils/insmod.c b/modutils/insmod.c index cef47ff45..3d9add19a 100644 --- a/modutils/insmod.c +++ b/modutils/insmod.c | |||
| @@ -368,23 +368,20 @@ enum { | |||
| 368 | /* The structures used in Linux 2.1. */ | 368 | /* The structures used in Linux 2.1. */ |
| 369 | 369 | ||
| 370 | /* Note: new_module_symbol does not use tgt_long intentionally */ | 370 | /* Note: new_module_symbol does not use tgt_long intentionally */ |
| 371 | struct new_module_symbol | 371 | struct new_module_symbol { |
| 372 | { | ||
| 373 | unsigned long value; | 372 | unsigned long value; |
| 374 | unsigned long name; | 373 | unsigned long name; |
| 375 | }; | 374 | }; |
| 376 | 375 | ||
| 377 | struct new_module_persist; | 376 | struct new_module_persist; |
| 378 | 377 | ||
| 379 | struct new_module_ref | 378 | struct new_module_ref { |
| 380 | { | ||
| 381 | unsigned tgt_long dep; /* kernel addresses */ | 379 | unsigned tgt_long dep; /* kernel addresses */ |
| 382 | unsigned tgt_long ref; | 380 | unsigned tgt_long ref; |
| 383 | unsigned tgt_long next_ref; | 381 | unsigned tgt_long next_ref; |
| 384 | }; | 382 | }; |
| 385 | 383 | ||
| 386 | struct new_module | 384 | struct new_module { |
| 387 | { | ||
| 388 | unsigned tgt_long size_of_struct; /* == sizeof(module) */ | 385 | unsigned tgt_long size_of_struct; /* == sizeof(module) */ |
| 389 | unsigned tgt_long next; | 386 | unsigned tgt_long next; |
| 390 | unsigned tgt_long name; | 387 | unsigned tgt_long name; |
| @@ -426,8 +423,7 @@ struct new_module | |||
| 426 | #define KALLSYMS_SEC_NAME "__kallsyms" | 423 | #define KALLSYMS_SEC_NAME "__kallsyms" |
| 427 | 424 | ||
| 428 | 425 | ||
| 429 | struct new_module_info | 426 | struct new_module_info { |
| 430 | { | ||
| 431 | unsigned long addr; | 427 | unsigned long addr; |
| 432 | unsigned long size; | 428 | unsigned long size; |
| 433 | unsigned long flags; | 429 | unsigned long flags; |
| @@ -561,8 +557,7 @@ struct obj_symbol | |||
| 561 | 557 | ||
| 562 | #define HASH_BUCKETS 521 | 558 | #define HASH_BUCKETS 521 |
| 563 | 559 | ||
| 564 | struct obj_file | 560 | struct obj_file { |
| 565 | { | ||
| 566 | ElfW(Ehdr) header; | 561 | ElfW(Ehdr) header; |
| 567 | ElfW(Addr) baseaddr; | 562 | ElfW(Addr) baseaddr; |
| 568 | struct obj_section **sections; | 563 | struct obj_section **sections; |
| @@ -577,24 +572,21 @@ struct obj_file | |||
| 577 | struct obj_symbol *symtab[HASH_BUCKETS]; | 572 | struct obj_symbol *symtab[HASH_BUCKETS]; |
| 578 | }; | 573 | }; |
| 579 | 574 | ||
| 580 | enum obj_reloc | 575 | enum obj_reloc { |
| 581 | { | ||
| 582 | obj_reloc_ok, | 576 | obj_reloc_ok, |
| 583 | obj_reloc_overflow, | 577 | obj_reloc_overflow, |
| 584 | obj_reloc_dangerous, | 578 | obj_reloc_dangerous, |
| 585 | obj_reloc_unhandled | 579 | obj_reloc_unhandled |
| 586 | }; | 580 | }; |
| 587 | 581 | ||
| 588 | struct obj_string_patch | 582 | struct obj_string_patch { |
| 589 | { | ||
| 590 | struct obj_string_patch *next; | 583 | struct obj_string_patch *next; |
| 591 | int reloc_secidx; | 584 | int reloc_secidx; |
| 592 | ElfW(Addr) reloc_offset; | 585 | ElfW(Addr) reloc_offset; |
| 593 | ElfW(Addr) string_offset; | 586 | ElfW(Addr) string_offset; |
| 594 | }; | 587 | }; |
| 595 | 588 | ||
| 596 | struct obj_symbol_patch | 589 | struct obj_symbol_patch { |
| 597 | { | ||
| 598 | struct obj_symbol_patch *next; | 590 | struct obj_symbol_patch *next; |
| 599 | int reloc_secidx; | 591 | int reloc_secidx; |
| 600 | ElfW(Addr) reloc_offset; | 592 | ElfW(Addr) reloc_offset; |
| @@ -805,12 +797,11 @@ static char *m_filename; | |||
| 805 | static char *m_fullName; | 797 | static char *m_fullName; |
| 806 | 798 | ||
| 807 | 799 | ||
| 808 | |||
| 809 | /*======================================================================*/ | 800 | /*======================================================================*/ |
| 810 | 801 | ||
| 811 | 802 | ||
| 812 | static int check_module_name_match(const char *filename, struct stat *statbuf, | 803 | static int check_module_name_match(const char *filename, struct stat *statbuf, |
| 813 | void *userdata) | 804 | void *userdata) |
| 814 | { | 805 | { |
| 815 | char *fullname = (char *) userdata; | 806 | char *fullname = (char *) userdata; |
| 816 | 807 | ||
| @@ -860,10 +851,10 @@ static struct obj_symbol *arch_new_symbol(void) | |||
| 860 | 851 | ||
| 861 | static enum obj_reloc | 852 | static enum obj_reloc |
| 862 | arch_apply_relocation(struct obj_file *f, | 853 | arch_apply_relocation(struct obj_file *f, |
| 863 | struct obj_section *targsec, | 854 | struct obj_section *targsec, |
| 864 | struct obj_section *symsec, | 855 | struct obj_section *symsec, |
| 865 | struct obj_symbol *sym, | 856 | struct obj_symbol *sym, |
| 866 | ElfW(RelM) *rel, ElfW(Addr) v) | 857 | ElfW(RelM) *rel, ElfW(Addr) v) |
| 867 | { | 858 | { |
| 868 | struct arch_file *ifile = (struct arch_file *) f; | 859 | struct arch_file *ifile = (struct arch_file *) f; |
| 869 | enum obj_reloc ret = obj_reloc_ok; | 860 | enum obj_reloc ret = obj_reloc_ok; |
| @@ -1856,64 +1847,64 @@ static void arch_create_got(struct obj_file *f) | |||
| 1856 | 1847 | ||
| 1857 | switch (ELF_R_TYPE(rel->r_info)) { | 1848 | switch (ELF_R_TYPE(rel->r_info)) { |
| 1858 | #if defined(__arm__) | 1849 | #if defined(__arm__) |
| 1859 | case R_ARM_PC24: | 1850 | case R_ARM_PC24: |
| 1860 | case R_ARM_PLT32: | 1851 | case R_ARM_PLT32: |
| 1861 | plt_allocate = 1; | 1852 | plt_allocate = 1; |
| 1862 | break; | 1853 | break; |
| 1863 | 1854 | ||
| 1864 | case R_ARM_GOTOFF: | 1855 | case R_ARM_GOTOFF: |
| 1865 | case R_ARM_GOTPC: | 1856 | case R_ARM_GOTPC: |
| 1866 | got_needed = 1; | 1857 | got_needed = 1; |
| 1867 | continue; | 1858 | continue; |
| 1868 | 1859 | ||
| 1869 | case R_ARM_GOT32: | 1860 | case R_ARM_GOT32: |
| 1870 | got_allocate = 1; | 1861 | got_allocate = 1; |
| 1871 | break; | 1862 | break; |
| 1872 | 1863 | ||
| 1873 | #elif defined(__i386__) | 1864 | #elif defined(__i386__) |
| 1874 | case R_386_GOTPC: | 1865 | case R_386_GOTPC: |
| 1875 | case R_386_GOTOFF: | 1866 | case R_386_GOTOFF: |
| 1876 | got_needed = 1; | 1867 | got_needed = 1; |
| 1877 | continue; | 1868 | continue; |
| 1878 | 1869 | ||
| 1879 | case R_386_GOT32: | 1870 | case R_386_GOT32: |
| 1880 | got_allocate = 1; | 1871 | got_allocate = 1; |
| 1881 | break; | 1872 | break; |
| 1882 | 1873 | ||
| 1883 | #elif defined(__powerpc__) | 1874 | #elif defined(__powerpc__) |
| 1884 | case R_PPC_REL24: | 1875 | case R_PPC_REL24: |
| 1885 | plt_allocate = 1; | 1876 | plt_allocate = 1; |
| 1886 | break; | 1877 | break; |
| 1887 | 1878 | ||
| 1888 | #elif defined(__mc68000__) | 1879 | #elif defined(__mc68000__) |
| 1889 | case R_68K_GOT32: | 1880 | case R_68K_GOT32: |
| 1890 | got_allocate = 1; | 1881 | got_allocate = 1; |
| 1891 | break; | 1882 | break; |
| 1892 | 1883 | ||
| 1893 | #ifdef R_68K_GOTOFF | 1884 | #ifdef R_68K_GOTOFF |
| 1894 | case R_68K_GOTOFF: | 1885 | case R_68K_GOTOFF: |
| 1895 | got_needed = 1; | 1886 | got_needed = 1; |
| 1896 | continue; | 1887 | continue; |
| 1897 | #endif | 1888 | #endif |
| 1898 | 1889 | ||
| 1899 | #elif defined(__sh__) | 1890 | #elif defined(__sh__) |
| 1900 | case R_SH_GOT32: | 1891 | case R_SH_GOT32: |
| 1901 | got_allocate = 1; | 1892 | got_allocate = 1; |
| 1902 | break; | 1893 | break; |
| 1903 | 1894 | ||
| 1904 | case R_SH_GOTPC: | 1895 | case R_SH_GOTPC: |
| 1905 | case R_SH_GOTOFF: | 1896 | case R_SH_GOTOFF: |
| 1906 | got_needed = 1; | 1897 | got_needed = 1; |
| 1907 | continue; | 1898 | continue; |
| 1908 | 1899 | ||
| 1909 | #elif defined (__v850e__) | 1900 | #elif defined (__v850e__) |
| 1910 | case R_V850_22_PCREL: | 1901 | case R_V850_22_PCREL: |
| 1911 | plt_needed = 1; | 1902 | plt_needed = 1; |
| 1912 | break; | 1903 | break; |
| 1913 | 1904 | ||
| 1914 | #endif | 1905 | #endif |
| 1915 | default: | 1906 | default: |
| 1916 | continue; | 1907 | continue; |
| 1917 | } | 1908 | } |
| 1918 | 1909 | ||
| 1919 | if (extsym->st_name != 0) { | 1910 | if (extsym->st_name != 0) { |
| @@ -2047,9 +2038,9 @@ obj_set_symbol_compare(struct obj_file *f, | |||
| 2047 | 2038 | ||
| 2048 | static struct obj_symbol * | 2039 | static struct obj_symbol * |
| 2049 | obj_add_symbol(struct obj_file *f, const char *name, | 2040 | obj_add_symbol(struct obj_file *f, const char *name, |
| 2050 | unsigned long symidx, int info, | 2041 | unsigned long symidx, int info, |
| 2051 | int secidx, ElfW(Addr) value, | 2042 | int secidx, ElfW(Addr) value, |
| 2052 | unsigned long size) | 2043 | unsigned long size) |
| 2053 | { | 2044 | { |
| 2054 | struct obj_symbol *sym; | 2045 | struct obj_symbol *sym; |
| 2055 | unsigned long hash = f->symbol_hash(name) % HASH_BUCKETS; | 2046 | unsigned long hash = f->symbol_hash(name) % HASH_BUCKETS; |
| @@ -2153,8 +2144,7 @@ obj_find_symbol(struct obj_file *f, const char *name) | |||
| 2153 | return NULL; | 2144 | return NULL; |
| 2154 | } | 2145 | } |
| 2155 | 2146 | ||
| 2156 | static ElfW(Addr) | 2147 | static ElfW(Addr) obj_symbol_final_value(struct obj_file * f, struct obj_symbol * sym) |
| 2157 | obj_symbol_final_value(struct obj_file * f, struct obj_symbol * sym) | ||
| 2158 | { | 2148 | { |
| 2159 | if (sym) { | 2149 | if (sym) { |
| 2160 | if (sym->secidx >= SHN_LORESERVE) | 2150 | if (sym->secidx >= SHN_LORESERVE) |
| @@ -2213,9 +2203,9 @@ obj_insert_section_load_order(struct obj_file *f, struct obj_section *sec) | |||
| 2213 | } | 2203 | } |
| 2214 | 2204 | ||
| 2215 | static struct obj_section *obj_create_alloced_section(struct obj_file *f, | 2205 | static struct obj_section *obj_create_alloced_section(struct obj_file *f, |
| 2216 | const char *name, | 2206 | const char *name, |
| 2217 | unsigned long align, | 2207 | unsigned long align, |
| 2218 | unsigned long size) | 2208 | unsigned long size) |
| 2219 | { | 2209 | { |
| 2220 | int newidx = f->header.e_shnum++; | 2210 | int newidx = f->header.e_shnum++; |
| 2221 | struct obj_section *sec; | 2211 | struct obj_section *sec; |
| @@ -2239,9 +2229,9 @@ static struct obj_section *obj_create_alloced_section(struct obj_file *f, | |||
| 2239 | } | 2229 | } |
| 2240 | 2230 | ||
| 2241 | static struct obj_section *obj_create_alloced_section_first(struct obj_file *f, | 2231 | static struct obj_section *obj_create_alloced_section_first(struct obj_file *f, |
| 2242 | const char *name, | 2232 | const char *name, |
| 2243 | unsigned long align, | 2233 | unsigned long align, |
| 2244 | unsigned long size) | 2234 | unsigned long size) |
| 2245 | { | 2235 | { |
| 2246 | int newidx = f->header.e_shnum++; | 2236 | int newidx = f->header.e_shnum++; |
| 2247 | struct obj_section *sec; | 2237 | struct obj_section *sec; |
| @@ -2478,50 +2468,50 @@ new_process_module_arguments(struct obj_file *f, int argc, char **argv) | |||
| 2478 | return 0; | 2468 | return 0; |
| 2479 | } else if (*q == '\\') | 2469 | } else if (*q == '\\') |
| 2480 | switch (*++q) { | 2470 | switch (*++q) { |
| 2481 | case 'a': | 2471 | case 'a': |
| 2482 | *r = '\a'; | 2472 | *r = '\a'; |
| 2483 | break; | 2473 | break; |
| 2484 | case 'b': | 2474 | case 'b': |
| 2485 | *r = '\b'; | 2475 | *r = '\b'; |
| 2486 | break; | 2476 | break; |
| 2487 | case 'e': | 2477 | case 'e': |
| 2488 | *r = '\033'; | 2478 | *r = '\033'; |
| 2489 | break; | 2479 | break; |
| 2490 | case 'f': | 2480 | case 'f': |
| 2491 | *r = '\f'; | 2481 | *r = '\f'; |
| 2492 | break; | 2482 | break; |
| 2493 | case 'n': | 2483 | case 'n': |
| 2494 | *r = '\n'; | 2484 | *r = '\n'; |
| 2495 | break; | 2485 | break; |
| 2496 | case 'r': | 2486 | case 'r': |
| 2497 | *r = '\r'; | 2487 | *r = '\r'; |
| 2498 | break; | 2488 | break; |
| 2499 | case 't': | 2489 | case 't': |
| 2500 | *r = '\t'; | 2490 | *r = '\t'; |
| 2501 | break; | 2491 | break; |
| 2502 | 2492 | ||
| 2503 | case '0': | 2493 | case '0': |
| 2504 | case '1': | 2494 | case '1': |
| 2505 | case '2': | 2495 | case '2': |
| 2506 | case '3': | 2496 | case '3': |
| 2507 | case '4': | 2497 | case '4': |
| 2508 | case '5': | 2498 | case '5': |
| 2509 | case '6': | 2499 | case '6': |
| 2510 | case '7': | 2500 | case '7': |
| 2511 | { | 2501 | { |
| 2512 | int c = *q - '0'; | 2502 | int c = *q - '0'; |
| 2513 | if (q[1] >= '0' && q[1] <= '7') { | 2503 | if (q[1] >= '0' && q[1] <= '7') { |
| 2504 | c = (c * 8) + *++q - '0'; | ||
| 2505 | if (q[1] >= '0' && q[1] <= '7') | ||
| 2514 | c = (c * 8) + *++q - '0'; | 2506 | c = (c * 8) + *++q - '0'; |
| 2515 | if (q[1] >= '0' && q[1] <= '7') | ||
| 2516 | c = (c * 8) + *++q - '0'; | ||
| 2517 | } | ||
| 2518 | *r = c; | ||
| 2519 | } | 2507 | } |
| 2520 | break; | 2508 | *r = c; |
| 2509 | } | ||
| 2510 | break; | ||
| 2521 | 2511 | ||
| 2522 | default: | 2512 | default: |
| 2523 | *r = *q; | 2513 | *r = *q; |
| 2524 | break; | 2514 | break; |
| 2525 | } else | 2515 | } else |
| 2526 | *r = *q; | 2516 | *r = *q; |
| 2527 | } | 2517 | } |
| @@ -2587,51 +2577,51 @@ new_process_module_arguments(struct obj_file *f, int argc, char **argv) | |||
| 2587 | } else { | 2577 | } else { |
| 2588 | long v = strtoul(q, &q, 0); | 2578 | long v = strtoul(q, &q, 0); |
| 2589 | switch (*p) { | 2579 | switch (*p) { |
| 2590 | case 'b': | 2580 | case 'b': |
| 2591 | *loc++ = v; | 2581 | *loc++ = v; |
| 2592 | break; | 2582 | break; |
| 2593 | case 'h': | 2583 | case 'h': |
| 2594 | *(short *) loc = v; | 2584 | *(short *) loc = v; |
| 2595 | loc += tgt_sizeof_short; | 2585 | loc += tgt_sizeof_short; |
| 2596 | break; | 2586 | break; |
| 2597 | case 'i': | 2587 | case 'i': |
| 2598 | *(int *) loc = v; | 2588 | *(int *) loc = v; |
| 2599 | loc += tgt_sizeof_int; | 2589 | loc += tgt_sizeof_int; |
| 2600 | break; | 2590 | break; |
| 2601 | case 'l': | 2591 | case 'l': |
| 2602 | *(long *) loc = v; | 2592 | *(long *) loc = v; |
| 2603 | loc += tgt_sizeof_long; | 2593 | loc += tgt_sizeof_long; |
| 2604 | break; | 2594 | break; |
| 2605 | 2595 | ||
| 2606 | default: | 2596 | default: |
| 2607 | bb_error_msg("unknown parameter type '%c' for %s", *p, key); | 2597 | bb_error_msg("unknown parameter type '%c' for %s", *p, key); |
| 2608 | return 0; | 2598 | return 0; |
| 2609 | } | 2599 | } |
| 2610 | } | 2600 | } |
| 2611 | 2601 | ||
| 2612 | retry_end_of_value: | 2602 | retry_end_of_value: |
| 2613 | switch (*q) { | 2603 | switch (*q) { |
| 2614 | case '\0': | 2604 | case '\0': |
| 2615 | goto end_of_arg; | 2605 | goto end_of_arg; |
| 2616 | 2606 | ||
| 2617 | case ' ': | 2607 | case ' ': |
| 2618 | case '\t': | 2608 | case '\t': |
| 2619 | case '\n': | 2609 | case '\n': |
| 2620 | case '\r': | 2610 | case '\r': |
| 2621 | ++q; | 2611 | ++q; |
| 2622 | goto retry_end_of_value; | 2612 | goto retry_end_of_value; |
| 2623 | 2613 | ||
| 2624 | case ',': | 2614 | case ',': |
| 2625 | if (++n > max) { | 2615 | if (++n > max) { |
| 2626 | bb_error_msg("too many values for %s (max %d)", key, max); | 2616 | bb_error_msg("too many values for %s (max %d)", key, max); |
| 2627 | return 0; | ||
| 2628 | } | ||
| 2629 | ++q; | ||
| 2630 | break; | ||
| 2631 | |||
| 2632 | default: | ||
| 2633 | bb_error_msg("invalid argument syntax for %s", key); | ||
| 2634 | return 0; | 2617 | return 0; |
| 2618 | } | ||
| 2619 | ++q; | ||
| 2620 | break; | ||
| 2621 | |||
| 2622 | default: | ||
| 2623 | bb_error_msg("invalid argument syntax for %s", key); | ||
| 2624 | return 0; | ||
| 2635 | } | 2625 | } |
| 2636 | } | 2626 | } |
| 2637 | 2627 | ||
| @@ -2712,7 +2702,7 @@ retry_modules_load: | |||
| 2712 | 2702 | ||
| 2713 | /* Collect the modules' symbols. */ | 2703 | /* Collect the modules' symbols. */ |
| 2714 | 2704 | ||
| 2715 | if (nmod){ | 2705 | if (nmod) { |
| 2716 | ext_modules = modules = xmalloc(nmod * sizeof(*modules)); | 2706 | ext_modules = modules = xmalloc(nmod * sizeof(*modules)); |
| 2717 | memset(modules, 0, nmod * sizeof(*modules)); | 2707 | memset(modules, 0, nmod * sizeof(*modules)); |
| 2718 | for (i = 0, mn = module_names, m = modules; | 2708 | for (i = 0, mn = module_names, m = modules; |
| @@ -2878,9 +2868,7 @@ static int new_create_module_ksymtab(struct obj_file *f) | |||
| 2878 | size_t nsyms; | 2868 | size_t nsyms; |
| 2879 | int *loaded; | 2869 | int *loaded; |
| 2880 | 2870 | ||
| 2881 | sec = | 2871 | sec = obj_create_alloced_section(f, "__ksymtab", tgt_sizeof_void_p, 0); |
| 2882 | obj_create_alloced_section(f, "__ksymtab", tgt_sizeof_void_p, | ||
| 2883 | 0); | ||
| 2884 | 2872 | ||
| 2885 | /* We don't want to export symbols residing in sections that | 2873 | /* We don't want to export symbols residing in sections that |
| 2886 | aren't loaded. There are a number of these created so that | 2874 | aren't loaded. There are a number of these created so that |
| @@ -3269,29 +3257,30 @@ static int obj_relocate(struct obj_file *f, ElfW(Addr) base) | |||
| 3269 | 3257 | ||
| 3270 | /* Do it! */ | 3258 | /* Do it! */ |
| 3271 | switch (arch_apply_relocation | 3259 | switch (arch_apply_relocation |
| 3272 | (f, targsec, symsec, intsym, rel, value)) { | 3260 | (f, targsec, symsec, intsym, rel, value) |
| 3273 | case obj_reloc_ok: | 3261 | ) { |
| 3274 | break; | 3262 | case obj_reloc_ok: |
| 3263 | break; | ||
| 3275 | 3264 | ||
| 3276 | case obj_reloc_overflow: | 3265 | case obj_reloc_overflow: |
| 3277 | errmsg = "Relocation overflow"; | 3266 | errmsg = "Relocation overflow"; |
| 3278 | goto bad_reloc; | 3267 | goto bad_reloc; |
| 3279 | case obj_reloc_dangerous: | 3268 | case obj_reloc_dangerous: |
| 3280 | errmsg = "Dangerous relocation"; | 3269 | errmsg = "Dangerous relocation"; |
| 3281 | goto bad_reloc; | 3270 | goto bad_reloc; |
| 3282 | case obj_reloc_unhandled: | 3271 | case obj_reloc_unhandled: |
| 3283 | errmsg = "Unhandled relocation"; | 3272 | errmsg = "Unhandled relocation"; |
| 3284 | bad_reloc: | 3273 | bad_reloc: |
| 3285 | if (extsym) { | 3274 | if (extsym) { |
| 3286 | bb_error_msg("%s of type %ld for %s", errmsg, | 3275 | bb_error_msg("%s of type %ld for %s", errmsg, |
| 3287 | (long) ELF_R_TYPE(rel->r_info), | 3276 | (long) ELF_R_TYPE(rel->r_info), |
| 3288 | strtab + extsym->st_name); | 3277 | strtab + extsym->st_name); |
| 3289 | } else { | 3278 | } else { |
| 3290 | bb_error_msg("%s of type %ld", errmsg, | 3279 | bb_error_msg("%s of type %ld", errmsg, |
| 3291 | (long) ELF_R_TYPE(rel->r_info)); | 3280 | (long) ELF_R_TYPE(rel->r_info)); |
| 3292 | } | 3281 | } |
| 3293 | ret = 0; | 3282 | ret = 0; |
| 3294 | break; | 3283 | break; |
| 3295 | } | 3284 | } |
| 3296 | } | 3285 | } |
| 3297 | } | 3286 | } |
| @@ -3419,7 +3408,8 @@ static struct obj_file *obj_load(FILE * fp, int loadprogbits) | |||
| 3419 | sec->header = section_headers[i]; | 3408 | sec->header = section_headers[i]; |
| 3420 | sec->idx = i; | 3409 | sec->idx = i; |
| 3421 | 3410 | ||
| 3422 | if(sec->header.sh_size) switch (sec->header.sh_type) { | 3411 | if(sec->header.sh_size) { |
| 3412 | switch (sec->header.sh_type) { | ||
| 3423 | case SHT_NULL: | 3413 | case SHT_NULL: |
| 3424 | case SHT_NOTE: | 3414 | case SHT_NOTE: |
| 3425 | case SHT_NOBITS: | 3415 | case SHT_NOBITS: |
| @@ -3470,6 +3460,7 @@ static struct obj_file *obj_load(FILE * fp, int loadprogbits) | |||
| 3470 | bb_error_msg("can't handle sections of type %ld", | 3460 | bb_error_msg("can't handle sections of type %ld", |
| 3471 | (long) sec->header.sh_type); | 3461 | (long) sec->header.sh_type); |
| 3472 | return NULL; | 3462 | return NULL; |
| 3463 | } | ||
| 3473 | } | 3464 | } |
| 3474 | } | 3465 | } |
| 3475 | 3466 | ||
| @@ -3495,67 +3486,66 @@ static struct obj_file *obj_load(FILE * fp, int loadprogbits) | |||
| 3495 | obj_insert_section_load_order(f, sec); | 3486 | obj_insert_section_load_order(f, sec); |
| 3496 | 3487 | ||
| 3497 | switch (sec->header.sh_type) { | 3488 | switch (sec->header.sh_type) { |
| 3498 | case SHT_SYMTAB: | 3489 | case SHT_SYMTAB: |
| 3499 | { | 3490 | { |
| 3500 | unsigned long nsym, j; | 3491 | unsigned long nsym, j; |
| 3501 | char *strtab; | 3492 | char *strtab; |
| 3502 | ElfW(Sym) * sym; | 3493 | ElfW(Sym) * sym; |
| 3503 | |||
| 3504 | if (sec->header.sh_entsize != sizeof(ElfW(Sym))) { | ||
| 3505 | bb_error_msg("symbol size mismatch: %lu != %lu", | ||
| 3506 | (unsigned long) sec->header.sh_entsize, | ||
| 3507 | (unsigned long) sizeof(ElfW(Sym))); | ||
| 3508 | return NULL; | ||
| 3509 | } | ||
| 3510 | 3494 | ||
| 3511 | nsym = sec->header.sh_size / sizeof(ElfW(Sym)); | 3495 | if (sec->header.sh_entsize != sizeof(ElfW(Sym))) { |
| 3512 | strtab = f->sections[sec->header.sh_link]->contents; | 3496 | bb_error_msg("symbol size mismatch: %lu != %lu", |
| 3513 | sym = (ElfW(Sym) *) sec->contents; | 3497 | (unsigned long) sec->header.sh_entsize, |
| 3514 | 3498 | (unsigned long) sizeof(ElfW(Sym))); | |
| 3515 | /* Allocate space for a table of local symbols. */ | 3499 | return NULL; |
| 3516 | j = f->local_symtab_size = sec->header.sh_info; | 3500 | } |
| 3517 | f->local_symtab = xzalloc(j * sizeof(struct obj_symbol *)); | ||
| 3518 | |||
| 3519 | /* Insert all symbols into the hash table. */ | ||
| 3520 | for (j = 1, ++sym; j < nsym; ++j, ++sym) { | ||
| 3521 | ElfW(Addr) val = sym->st_value; | ||
| 3522 | const char *name; | ||
| 3523 | if (sym->st_name) | ||
| 3524 | name = strtab + sym->st_name; | ||
| 3525 | else if (sym->st_shndx < shnum) | ||
| 3526 | name = f->sections[sym->st_shndx]->name; | ||
| 3527 | else | ||
| 3528 | continue; | ||
| 3529 | 3501 | ||
| 3502 | nsym = sec->header.sh_size / sizeof(ElfW(Sym)); | ||
| 3503 | strtab = f->sections[sec->header.sh_link]->contents; | ||
| 3504 | sym = (ElfW(Sym) *) sec->contents; | ||
| 3505 | |||
| 3506 | /* Allocate space for a table of local symbols. */ | ||
| 3507 | j = f->local_symtab_size = sec->header.sh_info; | ||
| 3508 | f->local_symtab = xzalloc(j * sizeof(struct obj_symbol *)); | ||
| 3509 | |||
| 3510 | /* Insert all symbols into the hash table. */ | ||
| 3511 | for (j = 1, ++sym; j < nsym; ++j, ++sym) { | ||
| 3512 | ElfW(Addr) val = sym->st_value; | ||
| 3513 | const char *name; | ||
| 3514 | if (sym->st_name) | ||
| 3515 | name = strtab + sym->st_name; | ||
| 3516 | else if (sym->st_shndx < shnum) | ||
| 3517 | name = f->sections[sym->st_shndx]->name; | ||
| 3518 | else | ||
| 3519 | continue; | ||
| 3530 | #if defined(__SH5__) | 3520 | #if defined(__SH5__) |
| 3531 | /* | 3521 | /* |
| 3532 | * For sh64 it is possible that the target of a branch | 3522 | * For sh64 it is possible that the target of a branch |
| 3533 | * requires a mode switch (32 to 16 and back again). | 3523 | * requires a mode switch (32 to 16 and back again). |
| 3534 | * | 3524 | * |
| 3535 | * This is implied by the lsb being set in the target | 3525 | * This is implied by the lsb being set in the target |
| 3536 | * address for SHmedia mode and clear for SHcompact. | 3526 | * address for SHmedia mode and clear for SHcompact. |
| 3537 | */ | 3527 | */ |
| 3538 | val |= sym->st_other & 4; | 3528 | val |= sym->st_other & 4; |
| 3539 | #endif | 3529 | #endif |
| 3540 | 3530 | ||
| 3541 | obj_add_symbol(f, name, j, sym->st_info, sym->st_shndx, | 3531 | obj_add_symbol(f, name, j, sym->st_info, sym->st_shndx, |
| 3542 | val, sym->st_size); | 3532 | val, sym->st_size); |
| 3543 | } | ||
| 3544 | } | 3533 | } |
| 3545 | break; | 3534 | } |
| 3535 | break; | ||
| 3546 | 3536 | ||
| 3547 | case SHT_RELM: | 3537 | case SHT_RELM: |
| 3548 | if (sec->header.sh_entsize != sizeof(ElfW(RelM))) { | 3538 | if (sec->header.sh_entsize != sizeof(ElfW(RelM))) { |
| 3549 | bb_error_msg("relocation entry size mismatch: %lu != %lu", | 3539 | bb_error_msg("relocation entry size mismatch: %lu != %lu", |
| 3550 | (unsigned long) sec->header.sh_entsize, | 3540 | (unsigned long) sec->header.sh_entsize, |
| 3551 | (unsigned long) sizeof(ElfW(RelM))); | 3541 | (unsigned long) sizeof(ElfW(RelM))); |
| 3552 | return NULL; | 3542 | return NULL; |
| 3553 | } | 3543 | } |
| 3554 | break; | 3544 | break; |
| 3555 | /* XXX Relocation code from modutils-2.3.19 is not here. | 3545 | /* XXX Relocation code from modutils-2.3.19 is not here. |
| 3556 | * Why? That's about 20 lines of code from obj/obj_load.c, | 3546 | * Why? That's about 20 lines of code from obj/obj_load.c, |
| 3557 | * which gets done in a second pass through the sections. | 3547 | * which gets done in a second pass through the sections. |
| 3558 | * This BusyBox insmod does similar work in obj_relocate(). */ | 3548 | * This BusyBox insmod does similar work in obj_relocate(). */ |
| 3559 | } | 3549 | } |
| 3560 | } | 3550 | } |
| 3561 | 3551 | ||
| @@ -3606,10 +3596,11 @@ static void hide_special_symbols(struct obj_file *f) | |||
| 3606 | struct obj_symbol *sym; | 3596 | struct obj_symbol *sym; |
| 3607 | const char *const *p; | 3597 | const char *const *p; |
| 3608 | 3598 | ||
| 3609 | for (p = specials; *p; ++p) | 3599 | for (p = specials; *p; ++p) { |
| 3610 | if ((sym = obj_find_symbol(f, *p)) != NULL) | 3600 | sym = obj_find_symbol(f, *p); |
| 3611 | sym->info = | 3601 | if (sym != NULL) |
| 3612 | ELF_ST_INFO(STB_LOCAL, ELF_ST_TYPE(sym->info)); | 3602 | sym->info = ELF_ST_INFO(STB_LOCAL, ELF_ST_TYPE(sym->info)); |
| 3603 | } | ||
| 3613 | } | 3604 | } |
| 3614 | 3605 | ||
| 3615 | 3606 | ||
| @@ -3629,12 +3620,14 @@ static int obj_gpl_license(struct obj_file *f, const char **license) | |||
| 3629 | "Dual MPL/GPL", | 3620 | "Dual MPL/GPL", |
| 3630 | }; | 3621 | }; |
| 3631 | 3622 | ||
| 3632 | if ((sec = obj_find_section(f, ".modinfo"))) { | 3623 | sec = obj_find_section(f, ".modinfo"); |
| 3624 | if (sec) { | ||
| 3633 | const char *value, *ptr, *endptr; | 3625 | const char *value, *ptr, *endptr; |
| 3634 | ptr = sec->contents; | 3626 | ptr = sec->contents; |
| 3635 | endptr = ptr + sec->header.sh_size; | 3627 | endptr = ptr + sec->header.sh_size; |
| 3636 | while (ptr < endptr) { | 3628 | while (ptr < endptr) { |
| 3637 | if ((value = strchr(ptr, '=')) && strncmp(ptr, "license", value-ptr) == 0) { | 3629 | value = strchr(ptr, '='); |
| 3630 | if (value && strncmp(ptr, "license", value-ptr) == 0) { | ||
| 3638 | int i; | 3631 | int i; |
| 3639 | if (license) | 3632 | if (license) |
| 3640 | *license = value+1; | 3633 | *license = value+1; |
| @@ -3690,7 +3683,8 @@ static void check_tainted_module(struct obj_file *f, char *m_name) | |||
| 3690 | const char *ptr; | 3683 | const char *ptr; |
| 3691 | 3684 | ||
| 3692 | kernel_has_tainted = 1; | 3685 | kernel_has_tainted = 1; |
| 3693 | if ((fd = open(tainted_file, O_RDWR)) < 0) { | 3686 | fd = open(tainted_file, O_RDWR); |
| 3687 | if (fd < 0) { | ||
| 3694 | if (errno == ENOENT) | 3688 | if (errno == ENOENT) |
| 3695 | kernel_has_tainted = 0; | 3689 | kernel_has_tainted = 0; |
| 3696 | else if (errno == EACCES) | 3690 | else if (errno == EACCES) |
| @@ -3957,7 +3951,7 @@ void print_load_map(struct obj_file *f); | |||
| 3957 | 3951 | ||
| 3958 | int insmod_main( int argc, char **argv) | 3952 | int insmod_main( int argc, char **argv) |
| 3959 | { | 3953 | { |
| 3960 | char *opt_o; | 3954 | char *opt_o, *arg1; |
| 3961 | int len; | 3955 | int len; |
| 3962 | int k_crcs; | 3956 | int k_crcs; |
| 3963 | char *tmp, *tmp1; | 3957 | char *tmp, *tmp1; |
| @@ -3983,17 +3977,18 @@ int insmod_main( int argc, char **argv) | |||
| 3983 | 3977 | ||
| 3984 | /* Parse any options */ | 3978 | /* Parse any options */ |
| 3985 | getopt32(argc, argv, OPTION_STR, &opt_o); | 3979 | getopt32(argc, argv, OPTION_STR, &opt_o); |
| 3980 | arg1 = argv[optind]; | ||
| 3986 | if (option_mask32 & OPT_o) { // -o /* name the output module */ | 3981 | if (option_mask32 & OPT_o) { // -o /* name the output module */ |
| 3987 | free(m_name); | 3982 | free(m_name); |
| 3988 | m_name = xstrdup(opt_o); | 3983 | m_name = xstrdup(opt_o); |
| 3989 | } | 3984 | } |
| 3990 | 3985 | ||
| 3991 | if (argv[optind] == NULL) { | 3986 | if (arg1 == NULL) { |
| 3992 | bb_show_usage(); | 3987 | bb_show_usage(); |
| 3993 | } | 3988 | } |
| 3994 | 3989 | ||
| 3995 | /* Grab the module name */ | 3990 | /* Grab the module name */ |
| 3996 | tmp1 = xstrdup(argv[optind]); | 3991 | tmp1 = xstrdup(arg1); |
| 3997 | tmp = basename(tmp1); | 3992 | tmp = basename(tmp1); |
| 3998 | len = strlen(tmp); | 3993 | len = strlen(tmp); |
| 3999 | 3994 | ||
| @@ -4004,15 +3999,15 @@ int insmod_main( int argc, char **argv) | |||
| 4004 | } | 3999 | } |
| 4005 | 4000 | ||
| 4006 | #if defined(CONFIG_FEATURE_2_6_MODULES) | 4001 | #if defined(CONFIG_FEATURE_2_6_MODULES) |
| 4007 | if (k_version > 4 && len > 3 && tmp[len - 3] == '.' && | 4002 | if (k_version > 4 && len > 3 && tmp[len - 3] == '.' |
| 4008 | tmp[len - 2] == 'k' && tmp[len - 1] == 'o') { | 4003 | && tmp[len - 2] == 'k' && tmp[len - 1] == 'o' |
| 4009 | len-=3; | 4004 | ) { |
| 4005 | len -= 3; | ||
| 4010 | tmp[len] = '\0'; | 4006 | tmp[len] = '\0'; |
| 4011 | } | 4007 | } else |
| 4012 | else | ||
| 4013 | #endif | 4008 | #endif |
| 4014 | if (len > 2 && tmp[len - 2] == '.' && tmp[len - 1] == 'o') { | 4009 | if (len > 2 && tmp[len - 2] == '.' && tmp[len - 1] == 'o') { |
| 4015 | len-=2; | 4010 | len -= 2; |
| 4016 | tmp[len] = '\0'; | 4011 | tmp[len] = '\0'; |
| 4017 | } | 4012 | } |
| 4018 | 4013 | ||
| @@ -4032,8 +4027,9 @@ int insmod_main( int argc, char **argv) | |||
| 4032 | } | 4027 | } |
| 4033 | 4028 | ||
| 4034 | /* Get a filedesc for the module. Check we we have a complete path */ | 4029 | /* Get a filedesc for the module. Check we we have a complete path */ |
| 4035 | if (stat(argv[optind], &st) < 0 || !S_ISREG(st.st_mode) || | 4030 | if (stat(arg1, &st) < 0 || !S_ISREG(st.st_mode) |
| 4036 | (fp = fopen(argv[optind], "r")) == NULL) { | 4031 | || (fp = fopen(arg1, "r")) == NULL |
| 4032 | ) { | ||
| 4037 | /* Hmm. Could not open it. First search under /lib/modules/`uname -r`, | 4033 | /* Hmm. Could not open it. First search under /lib/modules/`uname -r`, |
| 4038 | * but do not error out yet if we fail to find it... */ | 4034 | * but do not error out yet if we fail to find it... */ |
| 4039 | if (k_version) { /* uname succeedd */ | 4035 | if (k_version) { /* uname succeedd */ |
| @@ -4047,7 +4043,7 @@ int insmod_main( int argc, char **argv) | |||
| 4047 | * follow symlinks, but we do want to follow the | 4043 | * follow symlinks, but we do want to follow the |
| 4048 | * /lib/modules/`uname -r` dir, So resolve it ourselves | 4044 | * /lib/modules/`uname -r` dir, So resolve it ourselves |
| 4049 | * if it is a link... */ | 4045 | * if it is a link... */ |
| 4050 | if (realpath (tmdn, real_module_dir) == NULL) | 4046 | if (realpath(tmdn, real_module_dir) == NULL) |
| 4051 | module_dir = tmdn; | 4047 | module_dir = tmdn; |
| 4052 | else | 4048 | else |
| 4053 | module_dir = real_module_dir; | 4049 | module_dir = real_module_dir; |
| @@ -4057,8 +4053,7 @@ int insmod_main( int argc, char **argv) | |||
| 4057 | } | 4053 | } |
| 4058 | 4054 | ||
| 4059 | /* Check if we have found anything yet */ | 4055 | /* Check if we have found anything yet */ |
| 4060 | if (m_filename == 0 || ((fp = fopen(m_filename, "r")) == NULL)) | 4056 | if (m_filename == 0 || ((fp = fopen(m_filename, "r")) == NULL)) { |
| 4061 | { | ||
| 4062 | char module_dir[FILENAME_MAX]; | 4057 | char module_dir[FILENAME_MAX]; |
| 4063 | 4058 | ||
| 4064 | free(m_filename); | 4059 | free(m_filename); |
| @@ -4067,12 +4062,12 @@ int insmod_main( int argc, char **argv) | |||
| 4067 | strcpy(module_dir, _PATH_MODULES); | 4062 | strcpy(module_dir, _PATH_MODULES); |
| 4068 | /* No module found under /lib/modules/`uname -r`, this | 4063 | /* No module found under /lib/modules/`uname -r`, this |
| 4069 | * time cast the net a bit wider. Search /lib/modules/ */ | 4064 | * time cast the net a bit wider. Search /lib/modules/ */ |
| 4070 | if (! recursive_action(module_dir, TRUE, FALSE, FALSE, | 4065 | if (!recursive_action(module_dir, TRUE, FALSE, FALSE, |
| 4071 | check_module_name_match, 0, m_fullName)) | 4066 | check_module_name_match, 0, m_fullName) |
| 4072 | { | 4067 | ) { |
| 4073 | if (m_filename == 0 | 4068 | if (m_filename == 0 |
| 4074 | || ((fp = fopen(m_filename, "r")) == NULL)) | 4069 | || ((fp = fopen(m_filename, "r")) == NULL) |
| 4075 | { | 4070 | ) { |
| 4076 | bb_error_msg("%s: no module by that name found", m_fullName); | 4071 | bb_error_msg("%s: no module by that name found", m_fullName); |
| 4077 | goto out; | 4072 | goto out; |
| 4078 | } | 4073 | } |
| @@ -4080,22 +4075,22 @@ int insmod_main( int argc, char **argv) | |||
| 4080 | bb_error_msg_and_die("%s: no module by that name found", m_fullName); | 4075 | bb_error_msg_and_die("%s: no module by that name found", m_fullName); |
| 4081 | } | 4076 | } |
| 4082 | } else | 4077 | } else |
| 4083 | m_filename = xstrdup(argv[optind]); | 4078 | m_filename = xstrdup(arg1); |
| 4084 | 4079 | ||
| 4085 | if (flag_verbose) | 4080 | if (flag_verbose) |
| 4086 | printf("Using %s\n", m_filename); | 4081 | printf("Using %s\n", m_filename); |
| 4087 | 4082 | ||
| 4088 | #ifdef CONFIG_FEATURE_2_6_MODULES | 4083 | #ifdef CONFIG_FEATURE_2_6_MODULES |
| 4089 | if (k_version > 4) | 4084 | if (k_version > 4) { |
| 4090 | { | 4085 | argv[optind] = m_filename; |
| 4091 | optind--; | 4086 | optind--; |
| 4092 | argv[optind + 1] = m_filename; | ||
| 4093 | return insmod_ng_main(argc - optind, argv + optind); | 4087 | return insmod_ng_main(argc - optind, argv + optind); |
| 4094 | } | 4088 | } |
| 4095 | #endif | 4089 | #endif |
| 4096 | 4090 | ||
| 4097 | if ((f = obj_load(fp, LOADBITS)) == NULL) | 4091 | f = obj_load(fp, LOADBITS); |
| 4098 | bb_perror_msg_and_die("Could not load the module"); | 4092 | if (f == NULL) |
| 4093 | bb_perror_msg_and_die("cannot load the module"); | ||
| 4099 | 4094 | ||
| 4100 | if (get_modinfo_value(f, "kernel_version") == NULL) | 4095 | if (get_modinfo_value(f, "kernel_version") == NULL) |
| 4101 | m_has_modinfo = 0; | 4096 | m_has_modinfo = 0; |
| @@ -4157,8 +4152,7 @@ int insmod_main( int argc, char **argv) | |||
| 4157 | 4152 | ||
| 4158 | /* Allocate common symbols, symbol tables, and string tables. */ | 4153 | /* Allocate common symbols, symbol tables, and string tables. */ |
| 4159 | 4154 | ||
| 4160 | if (!new_create_this_module(f, m_name)) | 4155 | if (!new_create_this_module(f, m_name)) { |
| 4161 | { | ||
| 4162 | goto out; | 4156 | goto out; |
| 4163 | } | 4157 | } |
| 4164 | 4158 | ||
| @@ -4170,10 +4164,8 @@ int insmod_main( int argc, char **argv) | |||
| 4170 | 4164 | ||
| 4171 | /* done with the module name, on to the optional var=value arguments */ | 4165 | /* done with the module name, on to the optional var=value arguments */ |
| 4172 | ++optind; | 4166 | ++optind; |
| 4173 | |||
| 4174 | if (optind < argc) { | 4167 | if (optind < argc) { |
| 4175 | if (!new_process_module_arguments(f, argc - optind, argv + optind)) | 4168 | if (!new_process_module_arguments(f, argc - optind, argv + optind)) { |
| 4176 | { | ||
| 4177 | goto out; | 4169 | goto out; |
| 4178 | } | 4170 | } |
| 4179 | } | 4171 | } |
| @@ -4221,8 +4213,7 @@ int insmod_main( int argc, char **argv) | |||
| 4221 | goto out; | 4213 | goto out; |
| 4222 | } | 4214 | } |
| 4223 | 4215 | ||
| 4224 | if (!new_init_module(m_name, f, m_size)) | 4216 | if (!new_init_module(m_name, f, m_size)) { |
| 4225 | { | ||
| 4226 | delete_module(m_name); | 4217 | delete_module(m_name); |
| 4227 | goto out; | 4218 | goto out; |
| 4228 | } | 4219 | } |
| @@ -4259,16 +4250,16 @@ out: | |||
| 4259 | static const char *moderror(int err) | 4250 | static const char *moderror(int err) |
| 4260 | { | 4251 | { |
| 4261 | switch (err) { | 4252 | switch (err) { |
| 4262 | case ENOEXEC: | 4253 | case ENOEXEC: |
| 4263 | return "Invalid module format"; | 4254 | return "Invalid module format"; |
| 4264 | case ENOENT: | 4255 | case ENOENT: |
| 4265 | return "Unknown symbol in module"; | 4256 | return "Unknown symbol in module"; |
| 4266 | case ESRCH: | 4257 | case ESRCH: |
| 4267 | return "Module has wrong symbol version"; | 4258 | return "Module has wrong symbol version"; |
| 4268 | case EINVAL: | 4259 | case EINVAL: |
| 4269 | return "Invalid parameters"; | 4260 | return "Invalid parameters"; |
| 4270 | default: | 4261 | default: |
| 4271 | return strerror(err); | 4262 | return strerror(err); |
| 4272 | } | 4263 | } |
| 4273 | } | 4264 | } |
| 4274 | 4265 | ||
